diff options
Diffstat (limited to 'monitor.c')
-rw-r--r-- | monitor.c | 115 |
1 files changed, 106 insertions, 9 deletions
@@ -157,6 +157,8 @@ int mm_answer_gss_setup_ctx(int, Buffer *); | |||
157 | int mm_answer_gss_accept_ctx(int, Buffer *); | 157 | int mm_answer_gss_accept_ctx(int, Buffer *); |
158 | int mm_answer_gss_userok(int, Buffer *); | 158 | int mm_answer_gss_userok(int, Buffer *); |
159 | int mm_answer_gss_checkmic(int, Buffer *); | 159 | int mm_answer_gss_checkmic(int, Buffer *); |
160 | int mm_answer_gss_sign(int, Buffer *); | ||
161 | int mm_answer_gss_updatecreds(int, Buffer *); | ||
160 | #endif | 162 | #endif |
161 | 163 | ||
162 | #ifdef SSH_AUDIT_EVENTS | 164 | #ifdef SSH_AUDIT_EVENTS |
@@ -230,11 +232,18 @@ struct mon_table mon_dispatch_proto20[] = { | |||
230 | {MONITOR_REQ_GSSSTEP, 0, mm_answer_gss_accept_ctx}, | 232 | {MONITOR_REQ_GSSSTEP, 0, mm_answer_gss_accept_ctx}, |
231 | {MONITOR_REQ_GSSUSEROK, MON_ONCE|MON_AUTHDECIDE, mm_answer_gss_userok}, | 233 | {MONITOR_REQ_GSSUSEROK, MON_ONCE|MON_AUTHDECIDE, mm_answer_gss_userok}, |
232 | {MONITOR_REQ_GSSCHECKMIC, MON_ONCE, mm_answer_gss_checkmic}, | 234 | {MONITOR_REQ_GSSCHECKMIC, MON_ONCE, mm_answer_gss_checkmic}, |
235 | {MONITOR_REQ_GSSSIGN, MON_ONCE, mm_answer_gss_sign}, | ||
233 | #endif | 236 | #endif |
234 | {0, 0, NULL} | 237 | {0, 0, NULL} |
235 | }; | 238 | }; |
236 | 239 | ||
237 | struct mon_table mon_dispatch_postauth20[] = { | 240 | struct mon_table mon_dispatch_postauth20[] = { |
241 | #ifdef GSSAPI | ||
242 | {MONITOR_REQ_GSSSETUP, 0, mm_answer_gss_setup_ctx}, | ||
243 | {MONITOR_REQ_GSSSTEP, 0, mm_answer_gss_accept_ctx}, | ||
244 | {MONITOR_REQ_GSSSIGN, 0, mm_answer_gss_sign}, | ||
245 | {MONITOR_REQ_GSSUPCREDS, 0, mm_answer_gss_updatecreds}, | ||
246 | #endif | ||
238 | #ifdef WITH_OPENSSL | 247 | #ifdef WITH_OPENSSL |
239 | {MONITOR_REQ_MODULI, 0, mm_answer_moduli}, | 248 | {MONITOR_REQ_MODULI, 0, mm_answer_moduli}, |
240 | #endif | 249 | #endif |
@@ -302,6 +311,10 @@ monitor_child_preauth(Authctxt *_authctxt, struct monitor *pmonitor) | |||
302 | /* Permit requests for moduli and signatures */ | 311 | /* Permit requests for moduli and signatures */ |
303 | monitor_permit(mon_dispatch, MONITOR_REQ_MODULI, 1); | 312 | monitor_permit(mon_dispatch, MONITOR_REQ_MODULI, 1); |
304 | monitor_permit(mon_dispatch, MONITOR_REQ_SIGN, 1); | 313 | monitor_permit(mon_dispatch, MONITOR_REQ_SIGN, 1); |
314 | #ifdef GSSAPI | ||
315 | /* and for the GSSAPI key exchange */ | ||
316 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSSETUP, 1); | ||
317 | #endif | ||
305 | 318 | ||
306 | /* The first few requests do not require asynchronous access */ | 319 | /* The first few requests do not require asynchronous access */ |
307 | while (!authenticated) { | 320 | while (!authenticated) { |
@@ -408,6 +421,10 @@ monitor_child_postauth(struct monitor *pmonitor) | |||
408 | monitor_permit(mon_dispatch, MONITOR_REQ_MODULI, 1); | 421 | monitor_permit(mon_dispatch, MONITOR_REQ_MODULI, 1); |
409 | monitor_permit(mon_dispatch, MONITOR_REQ_SIGN, 1); | 422 | monitor_permit(mon_dispatch, MONITOR_REQ_SIGN, 1); |
410 | monitor_permit(mon_dispatch, MONITOR_REQ_TERM, 1); | 423 | monitor_permit(mon_dispatch, MONITOR_REQ_TERM, 1); |
424 | #ifdef GSSAPI | ||
425 | /* and for the GSSAPI key exchange */ | ||
426 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSSETUP, 1); | ||
427 | #endif | ||
411 | 428 | ||
412 | if (!no_pty_flag) { | 429 | if (!no_pty_flag) { |
413 | monitor_permit(mon_dispatch, MONITOR_REQ_PTY, 1); | 430 | monitor_permit(mon_dispatch, MONITOR_REQ_PTY, 1); |
@@ -1626,6 +1643,13 @@ monitor_apply_keystate(struct monitor *pmonitor) | |||
1626 | # endif | 1643 | # endif |
1627 | #endif /* WITH_OPENSSL */ | 1644 | #endif /* WITH_OPENSSL */ |
1628 | kex->kex[KEX_C25519_SHA256] = kexc25519_server; | 1645 | kex->kex[KEX_C25519_SHA256] = kexc25519_server; |
1646 | #ifdef GSSAPI | ||
1647 | if (options.gss_keyex) { | ||
1648 | kex->kex[KEX_GSS_GRP1_SHA1] = kexgss_server; | ||
1649 | kex->kex[KEX_GSS_GRP14_SHA1] = kexgss_server; | ||
1650 | kex->kex[KEX_GSS_GEX_SHA1] = kexgss_server; | ||
1651 | } | ||
1652 | #endif | ||
1629 | kex->load_host_public_key=&get_hostkey_public_by_type; | 1653 | kex->load_host_public_key=&get_hostkey_public_by_type; |
1630 | kex->load_host_private_key=&get_hostkey_private_by_type; | 1654 | kex->load_host_private_key=&get_hostkey_private_by_type; |
1631 | kex->host_key_index=&get_hostkey_index; | 1655 | kex->host_key_index=&get_hostkey_index; |
@@ -1714,8 +1738,8 @@ mm_answer_gss_setup_ctx(int sock, Buffer *m) | |||
1714 | OM_uint32 major; | 1738 | OM_uint32 major; |
1715 | u_int len; | 1739 | u_int len; |
1716 | 1740 | ||
1717 | if (!options.gss_authentication) | 1741 | if (!options.gss_authentication && !options.gss_keyex) |
1718 | fatal("%s: GSSAPI authentication not enabled", __func__); | 1742 | fatal("%s: GSSAPI not enabled", __func__); |
1719 | 1743 | ||
1720 | goid.elements = buffer_get_string(m, &len); | 1744 | goid.elements = buffer_get_string(m, &len); |
1721 | goid.length = len; | 1745 | goid.length = len; |
@@ -1744,8 +1768,8 @@ mm_answer_gss_accept_ctx(int sock, Buffer *m) | |||
1744 | OM_uint32 flags = 0; /* GSI needs this */ | 1768 | OM_uint32 flags = 0; /* GSI needs this */ |
1745 | u_int len; | 1769 | u_int len; |
1746 | 1770 | ||
1747 | if (!options.gss_authentication) | 1771 | if (!options.gss_authentication && !options.gss_keyex) |
1748 | fatal("%s: GSSAPI authentication not enabled", __func__); | 1772 | fatal("%s: GSSAPI not enabled", __func__); |
1749 | 1773 | ||
1750 | in.value = buffer_get_string(m, &len); | 1774 | in.value = buffer_get_string(m, &len); |
1751 | in.length = len; | 1775 | in.length = len; |
@@ -1764,6 +1788,7 @@ mm_answer_gss_accept_ctx(int sock, Buffer *m) | |||
1764 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSSTEP, 0); | 1788 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSSTEP, 0); |
1765 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSUSEROK, 1); | 1789 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSUSEROK, 1); |
1766 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSCHECKMIC, 1); | 1790 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSCHECKMIC, 1); |
1791 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSSIGN, 1); | ||
1767 | } | 1792 | } |
1768 | return (0); | 1793 | return (0); |
1769 | } | 1794 | } |
@@ -1775,8 +1800,8 @@ mm_answer_gss_checkmic(int sock, Buffer *m) | |||
1775 | OM_uint32 ret; | 1800 | OM_uint32 ret; |
1776 | u_int len; | 1801 | u_int len; |
1777 | 1802 | ||
1778 | if (!options.gss_authentication) | 1803 | if (!options.gss_authentication && !options.gss_keyex) |
1779 | fatal("%s: GSSAPI authentication not enabled", __func__); | 1804 | fatal("%s: GSSAPI not enabled", __func__); |
1780 | 1805 | ||
1781 | gssbuf.value = buffer_get_string(m, &len); | 1806 | gssbuf.value = buffer_get_string(m, &len); |
1782 | gssbuf.length = len; | 1807 | gssbuf.length = len; |
@@ -1805,10 +1830,11 @@ mm_answer_gss_userok(int sock, Buffer *m) | |||
1805 | int authenticated; | 1830 | int authenticated; |
1806 | const char *displayname; | 1831 | const char *displayname; |
1807 | 1832 | ||
1808 | if (!options.gss_authentication) | 1833 | if (!options.gss_authentication && !options.gss_keyex) |
1809 | fatal("%s: GSSAPI authentication not enabled", __func__); | 1834 | fatal("%s: GSSAPI not enabled", __func__); |
1810 | 1835 | ||
1811 | authenticated = authctxt->valid && ssh_gssapi_userok(authctxt->user); | 1836 | authenticated = authctxt->valid && |
1837 | ssh_gssapi_userok(authctxt->user, authctxt->pw); | ||
1812 | 1838 | ||
1813 | buffer_clear(m); | 1839 | buffer_clear(m); |
1814 | buffer_put_int(m, authenticated); | 1840 | buffer_put_int(m, authenticated); |
@@ -1824,5 +1850,76 @@ mm_answer_gss_userok(int sock, Buffer *m) | |||
1824 | /* Monitor loop will terminate if authenticated */ | 1850 | /* Monitor loop will terminate if authenticated */ |
1825 | return (authenticated); | 1851 | return (authenticated); |
1826 | } | 1852 | } |
1853 | |||
1854 | int | ||
1855 | mm_answer_gss_sign(int socket, Buffer *m) | ||
1856 | { | ||
1857 | gss_buffer_desc data; | ||
1858 | gss_buffer_desc hash = GSS_C_EMPTY_BUFFER; | ||
1859 | OM_uint32 major, minor; | ||
1860 | u_int len; | ||
1861 | |||
1862 | if (!options.gss_authentication && !options.gss_keyex) | ||
1863 | fatal("%s: GSSAPI not enabled", __func__); | ||
1864 | |||
1865 | data.value = buffer_get_string(m, &len); | ||
1866 | data.length = len; | ||
1867 | if (data.length != 20) | ||
1868 | fatal("%s: data length incorrect: %d", __func__, | ||
1869 | (int) data.length); | ||
1870 | |||
1871 | /* Save the session ID on the first time around */ | ||
1872 | if (session_id2_len == 0) { | ||
1873 | session_id2_len = data.length; | ||
1874 | session_id2 = xmalloc(session_id2_len); | ||
1875 | memcpy(session_id2, data.value, session_id2_len); | ||
1876 | } | ||
1877 | major = ssh_gssapi_sign(gsscontext, &data, &hash); | ||
1878 | |||
1879 | free(data.value); | ||
1880 | |||
1881 | buffer_clear(m); | ||
1882 | buffer_put_int(m, major); | ||
1883 | buffer_put_string(m, hash.value, hash.length); | ||
1884 | |||
1885 | mm_request_send(socket, MONITOR_ANS_GSSSIGN, m); | ||
1886 | |||
1887 | gss_release_buffer(&minor, &hash); | ||
1888 | |||
1889 | /* Turn on getpwnam permissions */ | ||
1890 | monitor_permit(mon_dispatch, MONITOR_REQ_PWNAM, 1); | ||
1891 | |||
1892 | /* And credential updating, for when rekeying */ | ||
1893 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSUPCREDS, 1); | ||
1894 | |||
1895 | return (0); | ||
1896 | } | ||
1897 | |||
1898 | int | ||
1899 | mm_answer_gss_updatecreds(int socket, Buffer *m) { | ||
1900 | ssh_gssapi_ccache store; | ||
1901 | int ok; | ||
1902 | |||
1903 | if (!options.gss_authentication && !options.gss_keyex) | ||
1904 | fatal("%s: GSSAPI not enabled", __func__); | ||
1905 | |||
1906 | store.filename = buffer_get_string(m, NULL); | ||
1907 | store.envvar = buffer_get_string(m, NULL); | ||
1908 | store.envval = buffer_get_string(m, NULL); | ||
1909 | |||
1910 | ok = ssh_gssapi_update_creds(&store); | ||
1911 | |||
1912 | free(store.filename); | ||
1913 | free(store.envvar); | ||
1914 | free(store.envval); | ||
1915 | |||
1916 | buffer_clear(m); | ||
1917 | buffer_put_int(m, ok); | ||
1918 | |||
1919 | mm_request_send(socket, MONITOR_ANS_GSSUPCREDS, m); | ||
1920 | |||
1921 | return(0); | ||
1922 | } | ||
1923 | |||
1827 | #endif /* GSSAPI */ | 1924 | #endif /* GSSAPI */ |
1828 | 1925 | ||