📄 pfkey_v2_parse.c
字号:
i, pfkey_alg->sadb_alg_id, SADB_EALG_MAX); SENDERR(EINVAL); } pfkey_alg++; } errlab: return error;}DEBUG_NO_STATIC intpfkey_spirange_parse(struct sadb_ext *pfkey_ext){ int error = 0; struct sadb_spirange *pfkey_spirange = (struct sadb_spirange *)pfkey_ext; /* sanity checks... */ if(pfkey_spirange->sadb_spirange_len != sizeof(struct sadb_spirange) / IPSEC_PFKEYv2_ALIGN) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_spirange_parse: " "size wrong ext_len=%d, key_ext_len=%d.\n", pfkey_spirange->sadb_spirange_len, (int)sizeof(struct sadb_spirange)); SENDERR(EINVAL); } if(pfkey_spirange->sadb_spirange_reserved) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_spirange_parse: " "reserved=%d must be set to zero.\n", pfkey_spirange->sadb_spirange_reserved); SENDERR(EINVAL); } if(ntohl(pfkey_spirange->sadb_spirange_max) < ntohl(pfkey_spirange->sadb_spirange_min)) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_spirange_parse: " "minspi=%08x must be < maxspi=%08x.\n", ntohl(pfkey_spirange->sadb_spirange_min), ntohl(pfkey_spirange->sadb_spirange_max)); SENDERR(EINVAL); } if(ntohl(pfkey_spirange->sadb_spirange_min) <= 255) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_spirange_parse: " "minspi=%08x must be > 255.\n", ntohl(pfkey_spirange->sadb_spirange_min)); SENDERR(EEXIST); } DEBUGGING(PF_KEY_DEBUG_PARSE_STRUCT, "pfkey_spirange_parse: " "ext_len=%u ext_type=%u(%s) min=%u max=%u res=%u.\n", pfkey_spirange->sadb_spirange_len, pfkey_spirange->sadb_spirange_exttype, pfkey_v2_sadb_ext_string(pfkey_spirange->sadb_spirange_exttype), pfkey_spirange->sadb_spirange_min, pfkey_spirange->sadb_spirange_max, pfkey_spirange->sadb_spirange_reserved); errlab: return error;}DEBUG_NO_STATIC intpfkey_x_kmprivate_parse(struct sadb_ext *pfkey_ext){ int error = 0; struct sadb_x_kmprivate *pfkey_x_kmprivate = (struct sadb_x_kmprivate *)pfkey_ext; /* sanity checks... */ if(pfkey_x_kmprivate->sadb_x_kmprivate_len < sizeof(struct sadb_x_kmprivate) / IPSEC_PFKEYv2_ALIGN) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_kmprivate_parse: " "size wrong ext_len=%d, key_ext_len=%d.\n", pfkey_x_kmprivate->sadb_x_kmprivate_len, (int)sizeof(struct sadb_x_kmprivate)); SENDERR(EINVAL); } if(pfkey_x_kmprivate->sadb_x_kmprivate_reserved) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_kmprivate_parse: " "reserved=%d must be set to zero.\n", pfkey_x_kmprivate->sadb_x_kmprivate_reserved); SENDERR(EINVAL); } DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_kmprivate_parse: " "Sorry, I can't parse exttype=%d yet.\n", pfkey_ext->sadb_ext_type); SENDERR(EINVAL); /* don't process these yet */errlab: return error;}DEBUG_NO_STATIC intpfkey_x_satype_parse(struct sadb_ext *pfkey_ext){ int error = 0; int i; struct sadb_x_satype *pfkey_x_satype = (struct sadb_x_satype *)pfkey_ext; DEBUGGING(PF_KEY_DEBUG_PARSE_FLOW, "pfkey_x_satype_parse: enter\n"); /* sanity checks... */ if(pfkey_x_satype->sadb_x_satype_len != sizeof(struct sadb_x_satype) / IPSEC_PFKEYv2_ALIGN) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_satype_parse: " "size wrong ext_len=%d, key_ext_len=%d.\n", pfkey_x_satype->sadb_x_satype_len, (int)sizeof(struct sadb_x_satype)); SENDERR(EINVAL); } if(!pfkey_x_satype->sadb_x_satype_satype) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_satype_parse: " "satype is zero, must be non-zero.\n"); SENDERR(EINVAL); } if(pfkey_x_satype->sadb_x_satype_satype > SADB_SATYPE_MAX) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_satype_parse: " "satype %d > max %d, invalid.\n", pfkey_x_satype->sadb_x_satype_satype, SADB_SATYPE_MAX); SENDERR(EINVAL); } if(!(satype2proto(pfkey_x_satype->sadb_x_satype_satype))) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_satype_parse: " "proto lookup from satype=%d failed.\n", pfkey_x_satype->sadb_x_satype_satype); SENDERR(EINVAL); } for(i = 0; i < 3; i++) { if(pfkey_x_satype->sadb_x_satype_reserved[i]) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_satype_parse: " "reserved[%d]=%d must be set to zero.\n", i, pfkey_x_satype->sadb_x_satype_reserved[i]); SENDERR(EINVAL); } } DEBUGGING(PF_KEY_DEBUG_PARSE_STRUCT, "pfkey_x_satype_parse: " "len=%u ext=%u(%s) satype=%u(%s) res=%u,%u,%u.\n", pfkey_x_satype->sadb_x_satype_len, pfkey_x_satype->sadb_x_satype_exttype, pfkey_v2_sadb_ext_string(pfkey_x_satype->sadb_x_satype_exttype), pfkey_x_satype->sadb_x_satype_satype, satype2name(pfkey_x_satype->sadb_x_satype_satype), pfkey_x_satype->sadb_x_satype_reserved[0], pfkey_x_satype->sadb_x_satype_reserved[1], pfkey_x_satype->sadb_x_satype_reserved[2]);errlab: return error;}DEBUG_NO_STATIC intpfkey_x_ext_debug_parse(struct sadb_ext *pfkey_ext){ int error = 0; int i; struct sadb_x_debug *pfkey_x_debug = (struct sadb_x_debug *)pfkey_ext; DEBUGGING(PF_KEY_DEBUG_PARSE_FLOW, "pfkey_x_debug_parse: enter\n"); /* sanity checks... */ if(pfkey_x_debug->sadb_x_debug_len != sizeof(struct sadb_x_debug) / IPSEC_PFKEYv2_ALIGN) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_debug_parse: " "size wrong ext_len=%d, key_ext_len=%d.\n", pfkey_x_debug->sadb_x_debug_len, (int)sizeof(struct sadb_x_debug)); SENDERR(EINVAL); } for(i = 0; i < 4; i++) { if(pfkey_x_debug->sadb_x_debug_reserved[i]) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_debug_parse: " "reserved[%d]=%d must be set to zero.\n", i, pfkey_x_debug->sadb_x_debug_reserved[i]); SENDERR(EINVAL); } } errlab: return error;}DEBUG_NO_STATIC intpfkey_x_ext_protocol_parse(struct sadb_ext *pfkey_ext){ int error = 0; struct sadb_protocol *p = (struct sadb_protocol *)pfkey_ext; DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_protocol_parse:\n"); /* sanity checks... */ if (p->sadb_protocol_len != sizeof(*p)/IPSEC_PFKEYv2_ALIGN) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_x_protocol_parse: size wrong ext_len=%d, key_ext_len=%d.\n", p->sadb_protocol_len, (int)sizeof(*p)); SENDERR(EINVAL); } if (p->sadb_protocol_reserved2 != 0) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_protocol_parse: res=%d, must be zero.\n", p->sadb_protocol_reserved2); SENDERR(EINVAL); } errlab: return error;}#ifdef NAT_TRAVERSALDEBUG_NO_STATIC intpfkey_x_ext_nat_t_type_parse(struct sadb_ext *pfkey_ext){ return 0;}DEBUG_NO_STATIC intpfkey_x_ext_nat_t_port_parse(struct sadb_ext *pfkey_ext){ return 0;}#endif#define DEFINEPARSER(NAME) static struct pf_key_ext_parsers_def NAME##_def={NAME, #NAME};DEFINEPARSER(pfkey_sa_parse);DEFINEPARSER(pfkey_lifetime_parse);DEFINEPARSER(pfkey_address_parse);DEFINEPARSER(pfkey_key_parse);DEFINEPARSER(pfkey_ident_parse);DEFINEPARSER(pfkey_sens_parse);DEFINEPARSER(pfkey_prop_parse);DEFINEPARSER(pfkey_supported_parse);DEFINEPARSER(pfkey_spirange_parse);DEFINEPARSER(pfkey_x_kmprivate_parse);DEFINEPARSER(pfkey_x_satype_parse);DEFINEPARSER(pfkey_x_ext_debug_parse);DEFINEPARSER(pfkey_x_ext_protocol_parse);#ifdef NAT_TRAVERSALDEFINEPARSER(pfkey_x_ext_nat_t_type_parse);DEFINEPARSER(pfkey_x_ext_nat_t_port_parse);#endifstruct pf_key_ext_parsers_def *ext_default_parsers[]={ NULL, /* pfkey_msg_parse, */ &pfkey_sa_parse_def, &pfkey_lifetime_parse_def, &pfkey_lifetime_parse_def, &pfkey_lifetime_parse_def, &pfkey_address_parse_def, &pfkey_address_parse_def, &pfkey_address_parse_def, &pfkey_key_parse_def, &pfkey_key_parse_def, &pfkey_ident_parse_def, &pfkey_ident_parse_def, &pfkey_sens_parse_def, &pfkey_prop_parse_def, &pfkey_supported_parse_def, &pfkey_supported_parse_def, &pfkey_spirange_parse_def, &pfkey_x_kmprivate_parse_def, &pfkey_x_satype_parse_def, &pfkey_sa_parse_def, &pfkey_address_parse_def, &pfkey_address_parse_def, &pfkey_address_parse_def, &pfkey_address_parse_def, &pfkey_address_parse_def, &pfkey_x_ext_debug_parse_def, &pfkey_x_ext_protocol_parse_def#ifdef NAT_TRAVERSAL , &pfkey_x_ext_nat_t_type_parse_def, &pfkey_x_ext_nat_t_port_parse_def, &pfkey_x_ext_nat_t_port_parse_def, &pfkey_address_parse_def#endif};intpfkey_msg_parse(struct sadb_msg *pfkey_msg, struct pf_key_ext_parsers_def *ext_parsers[], struct sadb_ext *extensions[], int dir){ int error = 0; int remain; struct sadb_ext *pfkey_ext; int extensions_seen = 0; DEBUGGING(PF_KEY_DEBUG_PARSE_STRUCT, "pfkey_msg_parse: " "parsing message ver=%d, type=%d(%s), errno=%d, satype=%d(%s), len=%d, res=%d, seq=%d, pid=%d.\n", pfkey_msg->sadb_msg_version, pfkey_msg->sadb_msg_type, pfkey_v2_sadb_type_string(pfkey_msg->sadb_msg_type), pfkey_msg->sadb_msg_errno, pfkey_msg->sadb_msg_satype, satype2name(pfkey_msg->sadb_msg_satype), pfkey_msg->sadb_msg_len, pfkey_msg->sadb_msg_reserved, pfkey_msg->sadb_msg_seq, pfkey_msg->sadb_msg_pid); if(ext_parsers == NULL) ext_parsers = ext_default_parsers; pfkey_extensions_init(extensions); remain = pfkey_msg->sadb_msg_len; remain -= sizeof(struct sadb_msg) / IPSEC_PFKEYv2_ALIGN; pfkey_ext = (struct sadb_ext*)((char*)pfkey_msg + sizeof(struct sadb_msg)); extensions[0] = (struct sadb_ext *) pfkey_msg; if(pfkey_msg->sadb_msg_version != PF_KEY_V2) { ERROR("pfkey_msg_parse: " "not PF_KEY_V2 msg, found %d, should be %d.\n", pfkey_msg->sadb_msg_version, PF_KEY_V2); SENDERR(EINVAL); } if(!pfkey_msg->sadb_msg_type) { ERROR("pfkey_msg_parse: " "msg type not set, must be non-zero..\n"); SENDERR(EINVAL); } if(pfkey_msg->sadb_msg_type > SADB_MAX) { ERROR("pfkey_msg_parse: " "msg type=%d > max=%d.\n", pfkey_msg->sadb_msg_type, SADB_MAX); SENDERR(EINVAL); } switch(pfkey_msg->sadb_msg_type) { case SADB_GETSPI: case SADB_UPDATE: case SADB_ADD: case SADB_DELETE: case SADB_GET: case SADB_X_GRPSA: case SADB_X_ADDFLOW: if(!satype2proto(pfkey_msg->sadb_msg_satype)) { ERROR("pfkey_msg_parse: " "satype %d conversion to proto failed for msg_type %d (%s).\n", pfkey_msg->sadb_msg_satype, pfkey_msg->sadb_msg_type, pfkey_v2_sadb_type_string(pfkey_msg->sadb_msg_type)); SENDERR(EINVAL); } else { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_msg_parse: " "satype %d(%s) conversion to proto gives %d for msg_type %d(%s).\n", pfkey_msg->sadb_msg_satype, satype2name(pfkey_msg->sadb_msg_satype), satype2proto(pfkey_msg->sadb_msg_satype), pfkey_msg->sadb_msg_type, pfkey_v2_sadb_type_string(pfkey_msg->sadb_msg_type)); } case SADB_ACQUIRE: case SADB_REGISTER: case SADB_EXPIRE: if(!pfkey_msg->sadb_msg_satype) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_msg_parse: " "satype is zero, must be non-zero for msg_type %d(%s).\n", pfkey_msg->sadb_msg_type, pfkey_v2_sadb_type_string(pfkey_msg->sadb_msg_type)); SENDERR(EINVAL); } default: break; } /* errno must not be set in downward messages */ /* this is not entirely true... a response to an ACQUIRE could return an error */ if((dir == EXT_BITS_IN) && (pfkey_msg->sadb_msg_type != SADB_ACQUIRE) && pfkey_msg->sadb_msg_errno) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_msg_parse: " "errno set to %d.\n", pfkey_msg->sadb_msg_errno); SENDERR(EINVAL); } DEBUGGING(PF_KEY_DEBUG_PARSE_FLOW, "pfkey_msg_parse: " "remain=%d\n", remain ); DEBUGGING(PF_KEY_DEBUG_PARSE_FLOW, "pfkey_msg_parse: " "extensions permitted=%08x, required=%08x.\n", extensions_bitmaps[dir][EXT_BITS_PERM][pfkey_msg->sadb_msg_type], extensions_bitmaps[dir][EXT_BITS_REQ][pfkey_msg->sadb_msg_type]); extensions_seen = 1; while( (remain * IPSEC_PFKEYv2_ALIGN) >= sizeof(struct sadb_ext) ) { /* Is there enough message left to support another extension header? */ if(remain < pfkey_ext->sadb_ext_len) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_msg_parse: " "remain %d less than ext len %d.\n", remain, pfkey_ext->sadb_ext_len); SENDERR(EINVAL); } DEBUGGING(PF_KEY_DEBUG_PARSE_FLOW, "pfkey_msg_parse: " "parsing ext type=%d(%s) remain=%d.\n", pfkey_ext->sadb_ext_type, pfkey_v2_sadb_ext_string(pfkey_ext->sadb_ext_type), remain); /* Is the extension header type valid? */ if((pfkey_ext->sadb_ext_type > SADB_EXT_MAX) || (!pfkey_ext->sadb_ext_type)) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_msg_parse: " "ext type %d(%s) invalid, SADB_EXT_MAX=%d.\n", pfkey_ext->sadb_ext_type, pfkey_v2_sadb_ext_string(pfkey_ext->sadb_ext_type), SADB_EXT_MAX); SENDERR(EINVAL); } /* Have we already seen this type of extension? */ if((extensions_seen & ( 1 << pfkey_ext->sadb_ext_type )) != 0) { DEBUGGING(PF_KEY_DEBUG_PARSE_PROBLEM, "pfkey_msg_parse: " "ext type %d(%s) already seen.\n",
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -