?? xauth.c
字號:
,pb_stream *rbody ,u_int16_t ap_id){ unsigned char *r_hash_start,*r_hashval; char xauth_username[64], xauth_password[64]; struct connection *c = st->st_connection; /* START_HASH_PAYLOAD(rbody, ISAKMP_NEXT_ATTR); */ { pb_stream hash_pbs; int np = ISAKMP_NEXT_ATTR; if (!out_generic(np, &isakmp_hash_desc, rbody, &hash_pbs)) return STF_INTERNAL_ERROR; r_hashval = hash_pbs.cur; /* remember where to plant value */ if (!out_zero(st->st_oakley.hasher->hash_digest_len, &hash_pbs, "HASH")) return STF_INTERNAL_ERROR; close_output_pbs(&hash_pbs); r_hash_start = (rbody)->cur; /* hash from after HASH payload */ } /* ATTR out */ { struct isakmp_mode_attr attrh; struct isakmp_attribute attr; pb_stream strattr,attrval; int attr_type; int dns_idx, wins_idx; bool dont_advance; attrh.isama_np = ISAKMP_NEXT_NONE; attrh.isama_type = ISAKMP_CFG_REPLY; attrh.isama_identifier = ap_id; if(!out_struct(&attrh, &isakmp_attr_desc, rbody, &strattr)) return STF_INTERNAL_ERROR; dns_idx = 0; wins_idx = 0; attr_type = XAUTH_TYPE; while(xauth_resp != 0) { dont_advance = FALSE; if(xauth_resp & 1) { /* ISAKMP attr out */ switch(attr_type) { case XAUTH_TYPE: attr.isaat_af_type = attr_type | ISAKMP_ATTR_AF_TV; attr.isaat_lv = XAUTH_TYPE_GENERIC; out_struct(&attr, &isakmp_xauth_attribute_desc, &strattr, NULL); break; case XAUTH_USER_NAME: attr.isaat_af_type = attr_type | ISAKMP_ATTR_AF_TLV; out_struct(&attr, &isakmp_xauth_attribute_desc, &strattr, &attrval); if(st->st_whack_sock == -1) { loglog(RC_LOG_SERIOUS, "XAUTH username requested, but no file descriptor available for prompt"); return STF_FAIL; } if(!whack_prompt_for(st->st_whack_sock , c->name, "Username", TRUE , xauth_username , sizeof(xauth_username))) { loglog(RC_LOG_SERIOUS, "XAUTH username prompt failed."); return STF_FAIL; } /* trip any trailing white space */ { char *u = xauth_username; strsep(&u, " \n\t"); } out_raw(xauth_username, strlen(xauth_username) ,&attrval, "XAUTH username"); close_output_pbs(&attrval); break; case XAUTH_USER_PASSWORD: attr.isaat_af_type = attr_type | ISAKMP_ATTR_AF_TLV; out_struct(&attr, &isakmp_xauth_attribute_desc, &strattr, &attrval); if(st->st_whack_sock == -1) { loglog(RC_LOG_SERIOUS, "XAUTH password requested, but no file descriptor available for prompt"); return STF_FAIL; } if(!whack_prompt_for(st->st_whack_sock , c->name, "Password", FALSE , xauth_password , sizeof(xauth_password))) { loglog(RC_LOG_SERIOUS, "XAUTH password prompt failed."); return STF_FAIL; } /* trip any trailing white space */ { char *u = xauth_password; strsep(&u, " \n\t"); } out_raw(xauth_password, strlen(xauth_password) ,&attrval, "XAUTH password"); close_output_pbs(&attrval); break; default: openswan_log("trying to send XAUTH reply, sending %s instead." , enum_show(&modecfg_attr_names, attr_type)); break; } } if (!dont_advance) { attr_type++; xauth_resp >>= 1; } } /* do not PAD here, */ close_output_pbs(&strattr); } openswan_log("XAUTH: Answering XAUTH challenge with user='%s'" , xauth_username); xauth_mode_cfg_hash(r_hashval, r_hash_start, rbody->cur, st); close_message(rbody); encrypt_message(rbody, st); return STF_OK;}/** * STATE_XAUTH_I0 * HDR*, HASH, ATTR(REQ=IP) --> HDR*, HASH, ATTR(REPLY=IP) * * This state occurs in initiator. * * In the initating client, it occurs in XAUTH, when the responding server * demands a password, and we have to supply it. * * @param md Message Digest * @return stf_status */stf_statusxauth_inI0(struct msg_digest *md){ struct state *const st = md->st; struct payload_digest *p; pb_stream *attrs; char msgbuf[81]; int len; unsigned type; char *dat; int status = 0; unsigned val; stf_status stat; bool gotrequest = FALSE; bool gotset = FALSE; bool got_status = FALSE; if(st->hidden_variables.st_xauth_client_done) { return modecfg_inI2(md); } DBG(DBG_CONTROLMORE, DBG_log("arrived in xauth_inI0")); st->st_msgid_phase15 = md->hdr.isa_msgid; CHECK_QUICK_HASH(md, xauth_mode_cfg_hash(hash_val ,hash_pbs->roof , md->message_pbs.roof, st) , "MODECFG-HASH", "XAUTH I0"); stat = STF_FAIL; /* process the MODECFG payloads therein */ for(p = md->chain[ISAKMP_NEXT_ATTR]; p != NULL; p = p->next) { struct isakmp_attribute attr; pb_stream strattr; unsigned int xauth_resp = LEMPTY;#define XAUTHLELEM(x) (LELEM(x - XAUTH_TYPE)) attrs = &p->pbs; switch(p->payload.attribute.isama_type) { default: openswan_log("Expecting ISAKMP_CFG_REQUEST, got %s instead (ignored)." , enum_name(&attr_msg_type_names , p->payload.attribute.isama_type)); case ISAKMP_CFG_SET: gotset = TRUE; break; case ISAKMP_CFG_REQUEST: gotrequest = TRUE; break; } while(attrs->cur < attrs->roof) { memset(&attr, 0, sizeof(attr)); if (!in_struct(&attr, &isakmp_xauth_attribute_desc , attrs, &strattr)) { /* Skip unknown */ int len; if (attr.isaat_af_type & 0x8000) len = 4; else len = attr.isaat_lv; if(len < 4) { openswan_log("Attribute was too short: %d", len); return STF_FAIL; } attrs->cur += len; continue; } if (attr.isaat_af_type & 0x8000) { len = 4; val = attr.isaat_lv; dat = NULL; } else { len = attr.isaat_lv; val = ntohs(*(u_int16_t *)strattr.cur); dat = strattr.cur; } switch(attr.isaat_af_type & ISAKMP_ATTR_RTYPE_MASK ) { case XAUTH_STATUS: got_status = TRUE; status = attr.isaat_lv; break; case XAUTH_MESSAGE: if(len > 80) len=80; memcpy(msgbuf, dat, len); msgbuf[len]='\0'; loglog(RC_LOG_SERIOUS, "XAUTH: Bad Message: %s", msgbuf); break; case XAUTH_TYPE: type = val; if(type != XAUTH_TYPE_GENERIC) { openswan_log("XAUTH: Unsupported type: %d", type); return STF_IGNORE; } xauth_resp |= XAUTHLELEM(attr.isaat_af_type); break; case XAUTH_USER_NAME: case XAUTH_USER_PASSWORD: xauth_resp |= XAUTHLELEM(attr.isaat_af_type); break; case INTERNAL_IP4_ADDRESS: case INTERNAL_IP4_NETMASK: case INTERNAL_IP4_DNS: case INTERNAL_IP4_SUBNET: case INTERNAL_IP4_NBNS: xauth_resp |= LELEM(attr.isaat_af_type); break; default: openswan_log("XAUTH: Unsupported attribute: %s" , enum_show(&modecfg_attr_names, (attr.isaat_af_type & ISAKMP_ATTR_RTYPE_MASK))); break; } } if(gotset && got_status) { /* ACK whatever it was that we got */ stat = xauth_client_ackstatus(st, &md->rbody ,md->chain[ISAKMP_NEXT_ATTR]->payload.attribute.isama_identifier); /* must have gotten a status */ if(status && stat == STF_OK) { st->hidden_variables.st_xauth_client_done = TRUE; openswan_log("XAUTH: Successfully Authenticated"); st->st_oakley.xauth = 0; return STF_OK; } else { return STF_FATAL; } } if(gotrequest) { if(xauth_resp & (XAUTHLELEM(XAUTH_USER_NAME)|XAUTHLELEM(XAUTH_USER_PASSWORD))) { DBG(DBG_CONTROL, DBG_log("XAUTH: Username/password request received")); } /* sanitize what we were asked to reply to */ if(st->st_connection->spd.this.xauth_client && (xauth_resp &( XAUTHLELEM(XAUTH_USER_NAME) | XAUTHLELEM(XAUTH_USER_PASSWORD)))==0) { openswan_log("XAUTH: No username/password request was received."); return STF_IGNORE; } /* now, opposite */ if(!st->st_connection->spd.this.xauth_client && (xauth_resp & (XAUTHLELEM(XAUTH_USER_NAME) |XAUTHLELEM(XAUTH_USER_PASSWORD)))!=0) { openswan_log("XAUTH: Username/password request was received, but XAUTH client mode not enabled."); return STF_IGNORE; } stat = xauth_client_resp(st, xauth_resp , &md->rbody ,md->chain[ISAKMP_NEXT_ATTR]->payload.attribute.isama_identifier); } if(stat != STF_OK) { /* notification payload - not exactly the right choice, but okay */ md->note = CERTIFICATE_UNAVAILABLE; return stat; } } /* reset the message ID */ st->st_msgid_phase15b = st->st_msgid_phase15; st->st_msgid_phase15 = 0; DBG(DBG_CONTROLMORE, DBG_log("xauth_inI0(STF_OK)")); return STF_OK;}/** XAUTH client code - Acknowledge status * * @param st State * @param rbody Response Body * @param ap_id * @return stf_status */stf_status xauth_client_ackstatus(struct state *st ,pb_stream *rbody ,u_int16_t ap_id){ unsigned char *r_hash_start,*r_hashval; /* START_HASH_PAYLOAD(rbody, ISAKMP_NEXT_ATTR); */ { pb_stream hash_pbs; int np = ISAKMP_NEXT_ATTR; if (!out_generic(np, &isakmp_hash_desc, rbody, &hash_pbs)) return STF_INTERNAL_ERROR; r_hashval = hash_pbs.cur; /* remember where to plant value */ if (!out_zero(st->st_oakley.hasher->hash_digest_len, &hash_pbs, "HASH")) return STF_INTERNAL_ERROR; close_output_pbs(&hash_pbs); r_hash_start = (rbody)->cur; /* hash from after HASH payload */ } /* ATTR out */ { struct isakmp_mode_attr attrh; struct isakmp_attribute attr; pb_stream strattr,attrval; int attr_type; int dns_idx, wins_idx; attrh.isama_np = ISAKMP_NEXT_NONE; attrh.isama_type = ISAKMP_CFG_ACK; attrh.isama_identifier = ap_id; if(!out_struct(&attrh, &isakmp_attr_desc, rbody, &strattr)) return STF_INTERNAL_ERROR; dns_idx = 0; wins_idx = 0; attr_type = XAUTH_TYPE; /* ISAKMP attr out */ attr.isaat_af_type = XAUTH_STATUS | ISAKMP_ATTR_AF_TV; attr.isaat_lv = 1; out_struct(&attr, &isakmp_xauth_attribute_desc, &strattr, &attrval); close_output_pbs(&attrval); close_message(&strattr); } xauth_mode_cfg_hash(r_hashval,r_hash_start,rbody->cur,st); close_message(rbody); encrypt_message(rbody, st); return STF_OK;}/** STATE_XAUTH_I1 * HDR*, HASH, ATTR(SET=IP) --> HDR*, HASH, ATTR(ACK,OK) * * @param md Message Digest * @return stf_status */stf_statusxauth_inI1(struct msg_digest *md){ struct state *const st = md->st; pb_stream *attrs = &md->chain[ISAKMP_NEXT_ATTR]->pbs; bool got_status, status; stf_status stat; struct payload_digest *p; unsigned int xauth_resp = LEMPTY; if(st->hidden_variables.st_xauth_client_done) { return modecfg_inI2(md); } DBG(DBG_CONTROLMORE, DBG_log("xauth_inI1")); st->st_msgid_phase15 = md->hdr.isa_msgid; CHECK_QUICK_HASH(md , xauth_mode_cfg_hash(hash_val ,hash_pbs->roof , md->message_pbs.roof, st) , "MODECFG-HASH", "XAUTH I1"); got_status = FALSE; status = FALSE; for(p = md->chain[ISAKMP_NEXT_ATTR]; p != NULL; p = p->next) { struct isakmp_attribute attr; pb_stream strattr; attrs = &p->pbs; switch(p->payload.attribute.isama_type) { default: openswan_log("Expecting MODE_CFG_SET, got %x instead." , p->payload.attribute.isama_type); return STF_IGNORE; case ISAKMP_CFG_SET: /* CHECK that SET has been received. */ while(attrs->cur < attrs->roof) { memset(&attr, 0, sizeof(attr)); if (!in_struct(&attr, &isakmp_xauth_attribute_desc , attrs, &strattr)) { /* Skip unknown */ int len; if (attr.isaat_af_type & 0x8000) len = 4; else len = attr.isaat_lv; if(len < 4) { openswan_log("Attribute was too short: %d", len); return STF_FAIL; } attrs->cur += len; } switch(attr.isaat_af_type & ISAKMP_ATTR_RTYPE_MASK ) { case XAUTH_STATUS: xauth_resp |= XAUTHLELEM(attr.isaat_af_type); got_status = TRUE; status = attr.isaat_lv; break; default: openswan_log("while waiting for XAUTH_STATUS, got %s instead." , enum_show(&modecfg_attr_names, (attr.isaat_af_type & ISAKMP_ATTR_RTYPE_MASK))); break; } } break; } } /* first check if we might be done! */ if(!got_status || status==FALSE) { /* oops, something seriously wrong */ openswan_log("did not get status attribute in xauth_inI1, looking for new challenge."); st->st_state = STATE_XAUTH_I0; return xauth_inI0(md); } /* ACK whatever it was that we got */ stat = xauth_client_ackstatus(st, &md->rbody ,md->chain[ISAKMP_NEXT_ATTR]->payload.attribute.isama_identifier); /* must have gotten a status */ if(status && stat == STF_OK) { st->hidden_variables.st_xauth_client_done = TRUE; openswan_log("successfully logged in"); st->st_oakley.xauth = 0; return STF_OK; } /* what? */ return stat;}/* * $Id: xauth.c,v 1.41.4.3 2005/07/26 02:11:23 ken Exp $ * * $Log: xauth.c,v $ * Revision 1.41.4.3 2005/07/26 02:11:23 ken * Pullin from HEAD: * Split Aggressive mode into ikev1_aggr.c * Fix NAT-T that we broke in dr7 * Move dpd/pgp vendor id's to vendor.[ch] * * Revision 1.41.4.2 2005/07/25 19:26:34 ken * Pullin fixes for NAT-T from HEAD * Includes IMPAIR_JACOB_TWO_TWO impairment from HEAD * change from c->interface to st->st_interface for sending packets * * Revision 1.43 2005/07/22 14:05:51 mcr * fixes for -Werror warnings. * * Revision 1.42 2005/07/22 14:00:19 mcr * fixes for -Werror warnings. * * Revision 1.41 2005/02/16 17:27:41 mcr * moved recording of xauth username to after the username * has actually been authenticated. * Do not record username on client -- I don't think that this * makes any sense. If it is important, it should be recorded * (and expressed in do_command()) in a different way. * * Revision 1.40 2005/02/14 05:58:46 ken * Add support for saving the XAUTH username, and then passing it to _updown as PLUTO_XAUTH_USERNAME environment variable * * Revision 1.39 2005/01/26 07:01:55 mcr * use phase1.5 msgid instead of msgid. * * * Local Variables: * c-basic-offset:4 * c-style: pluto * End: */
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -