static int mpoa_egress_cache_purge_reply( uint8_t * buff ){ int pos = 0; struct nhrp_fixed_h *fixed = (struct nhrp_fixed_h *)buff; struct nhrp_common_h *common; struct nhrp_cie *cie; struct extension_values values; struct k_message msg; memset(&values, 0, sizeof(struct extension_values)); memset(&msg,0,sizeof(struct k_message)); pos += sizeof(struct nhrp_fixed_h); common = (struct nhrp_common_h*)(buff + pos); if(!check_incoming(ntohl(common->request_ID), MPOA_EGRESS_CACHE_PURGE_REQUEST)) return -1; pos += sizeof(struct nhrp_common_h); cie = (struct nhrp_cie *)(buff + pos); msg.ip_mask = calculate_ip_mask(cie->prefix_length); if(fixed->ar_extoff) parse_extensions(buff + ntohs(fixed->ar_extoff),&values); else { printf("mpcd: p_recogn.c: warning: "); printf("no extensions in MPOA Egress Cache Purge Reply\n"); return -1; } if (values.dll_header_present == 0) { printf("mpcd: p_recogn.c: warning: "); printf("DLL Header Extension missing in MPOA Egress Cache Purge Reply\n"); return -1; } msg.content.eg_info.cache_id = values.dll_ext.cache_id; msg.type = EGRESS_PURGE_RCVD; memcpy(msg.MPS_ctrl,mpc_control.MPS_CTRL_ATM_ADDR,ATM_ESA_LEN); return send_to_kernel(&msg); }
static int mpoa_trigger( uint8_t * buff ){ int pos = 0; struct k_message msg; struct nhrp_common_h *common; struct extension_values values; struct nhrp_fixed_h *fixed = (struct nhrp_fixed_h*)buff; memset(&values, 0, sizeof(struct extension_values)); pos += sizeof(struct nhrp_fixed_h); common = (struct nhrp_common_h *)(buff + pos); pos += sizeof(struct nhrp_common_h); memset(&msg,0,sizeof(struct k_message)); if(ntohs(fixed->ar_extoff)) { printf("mpcd: p_recogn.c: mpoa_trigger: ar$extoff in Fixed Header != 0\n" ); parse_extensions(buff+ntohs(fixed->ar_extoff),&values); } if(!common->dst_proto_len){ printf("mpcd: p_recogn.c: mpoa_trigger: no destination ip to trigger! \n"); return -1; } if(common->src_proto_len) msg.content.in_info.in_dst_ip = common->dst_protocol_address; /* * If src_proto_len == 0 dst_protocol_address is found in "place" * of dst_ptocol_address. */ else msg.content.in_info.in_dst_ip = common->src_protocol_address; memcpy(msg.MPS_ctrl,mpc_control.MPS_CTRL_ATM_ADDR,ATM_ESA_LEN); msg.type = MPOA_TRIGGER_RCVD; send_to_kernel(&msg); return 1; }
static int nhrp_purge_request(uint8_t *buff){ int pos = 0; int cie_limit = 0; uint32_t ip_mask; uint8_t eg_MPC_data_ATM_addr[ATM_ESA_LEN]; uint32_t eg_MPS_ip_addr; uint32_t purge_ip; struct k_message msg; struct extension_values values; struct nhrp_common_h_no_ip *common_no_ip; struct nhrp_cie_no_nbma *cie_no_nbma; struct nhrp_cie *cie; struct nhrp_fixed_h *fixed = (struct nhrp_fixed_h *)buff; memset(&msg,0,sizeof(struct k_message)); if(ntohs(fixed->ar_extoff)){ cie_limit = ntohs(fixed->ar_extoff); } else{ cie_limit = ntohs(fixed->ar_pktsz); } pos += sizeof(struct nhrp_fixed_h); common_no_ip = (struct nhrp_common_h_no_ip *)(buff + pos); memcpy(eg_MPC_data_ATM_addr, common_no_ip->src_nbma_address ,ATM_ESA_LEN); pos += sizeof(struct nhrp_common_h_no_ip); if(common_no_ip->src_proto_len == PROTO_LEN_IP){ eg_MPS_ip_addr = ntohl((uint32_t)*(buff + pos)); pos += sizeof(eg_MPS_ip_addr); } if(common_no_ip->dst_proto_len == PROTO_LEN_IP) pos += sizeof(uint32_t); while(pos < cie_limit){ cie = (struct nhrp_cie *)(buff + pos); if(cie->cli_addr_tl){ purge_ip = cie->cli_protocol_address; ip_mask = calculate_ip_mask(cie->prefix_length); pos += sizeof(struct nhrp_cie); } else{ cie_no_nbma = (struct nhrp_cie_no_nbma *)(buff + pos); purge_ip = cie_no_nbma->cli_protocol_address; ip_mask = calculate_ip_mask(cie_no_nbma->prefix_length); pos += sizeof(struct nhrp_cie_no_nbma); } msg.type = INGRESS_PURGE_RCVD; msg.ip_mask = ip_mask; msg.content.in_info.in_dst_ip = purge_ip; memcpy(msg.MPS_ctrl, mpc_control.MPS_CTRL_ATM_ADDR, ATM_ESA_LEN); send_to_kernel(&msg); } /* we really do not do anything with the extensions, just parse them */ if(ntohs(fixed->ar_extoff)){ pos += parse_extensions(buff + ntohs(fixed->ar_extoff), &values); } if(!(ntohs(common_no_ip->flags) & FLAG_N )) return send_purge_reply(buff); return 1; }
static int mpoa_resolution_reply( uint8_t * buff ){ int pos = 0; struct k_message msg; struct extension_values values; struct nhrp_common_h *common; struct nhrp_cie *cie; struct nhrp_fixed_h *fixed = (struct nhrp_fixed_h*)buff; memset(&values, 0, sizeof(struct extension_values)); memset(&msg,0,sizeof(struct k_message)); pos += sizeof(struct nhrp_fixed_h); common = (struct nhrp_common_h*)(buff + pos); if(!check_incoming(ntohl(common->request_ID),MPOA_RESOLUTION_REQUEST)) return -1; pos += sizeof(struct nhrp_common_h); cie = (struct nhrp_cie*)(buff + pos); if(cie->code){ print_cie_code(cie->code); return -1; } msg.content.in_info.holding_time = ntohs(cie->holding_time); if(fixed->ar_extoff) pos += parse_extensions(buff + ntohs(fixed->ar_extoff), &values); if (values.egress_cache_tag_ext_present == 0) { printf("mpcd: p_recogn.c: warning: "); printf("received MPOA Resolution Reply "); printf("with no Egress Cache Tag Extension\n"); } if(values.tag_present && values.tag == 0) { printf("mpcd: p_recogn.c: warning: "); printf("received MPOA Resolution Reply "); printf("with Egress Cache Tag Extension where tag == 0\n"); values.tag_present = 0; } if(values.tag_present){ msg.content.in_info.tag = values.tag; } msg.type = MPOA_RES_REPLY_RCVD; msg.content.in_info.in_dst_ip = common->dst_protocol_address; memcpy(msg.content.in_info.eg_MPC_ATM_addr,cie->cli_nbma_address,ATM_ESA_LEN); memcpy(msg.MPS_ctrl,mpc_control.MPS_CTRL_ATM_ADDR, ATM_ESA_LEN); if(values.service_category_present) msg.qos.txtp.traffic_class = service_category_to_traff_class(values.service_category); else msg.qos.txtp.traffic_class = ATM_UBR; send_to_kernel(&msg); keep_alive_sm_running = 1; return MPOA_RESOLUTION_REPLY; }
static int mpoa_cache_imposition_request( uint8_t * buff ){ int pos = 0; struct k_message msg; struct nhrp_fixed_h * fixed = (struct nhrp_fixed_h *)buff; struct nhrp_common_h * common; struct nhrp_cie_short * cie_short; struct extension_values values; pos += sizeof( struct nhrp_fixed_h ); memset(&values, 0, sizeof(struct extension_values)); memset(&msg,0,sizeof(struct k_message)); common = (struct nhrp_common_h *)(buff + pos); memcpy(msg.content.eg_info.in_MPC_data_ATM_addr, common->src_nbma_address ,ATM_ESA_LEN); pos += sizeof(struct nhrp_common_h); cie_short = (struct nhrp_cie_short *)(buff + pos); msg.content.eg_info.holding_time = ntohs(cie_short->holding_time); msg.ip_mask = calculate_ip_mask(cie_short->prefix_length); if(ntohs(fixed->ar_extoff)){ pos += parse_extensions(buff + ntohs(fixed->ar_extoff), &values); } if(ntohs(cie_short->holding_time)) { if (values.dll_header_present == 0) { printf("mpcd: p_recogn.c: warning: "); printf("holding time non-zero but MPOA DLL Header Extension missing\n"); return 0; } keep_alive_sm_running = 1; } msg.content.eg_info.cache_id = values.dll_ext.cache_id; msg.content.eg_info.DH_length = values.dll_ext.dh_length; memcpy(msg.content.eg_info.DLL_header, values.dll_ext.dll_header, msg.content.eg_info.DH_length); if(common->src_proto_len) msg.content.eg_info.mps_ip = common->src_protocol_address; if(common->dst_proto_len) msg.content.eg_info.eg_dst_ip = common->dst_protocol_address; msg.content.eg_info.tag = new_tag(msg.content.eg_info.cache_id); memcpy(msg.MPS_ctrl, mpc_control.MPS_CTRL_ATM_ADDR, ATM_ESA_LEN); msg.type = CACHE_IMPOS_RCVD; send_to_kernel(&msg); return send_cache_imposition_reply( buff, msg.content.eg_info.tag, 0x00, 0, MTU_DEFAULT, common->src_nbma_address ); }
static int mpoa_keep_alive(uint8_t *buff){ int pos = 0; uint32_t sequence_nmbr; struct nhrp_fixed_h *fixed = (struct nhrp_fixed_h *)buff; struct extension_values values; struct nhrp_common_h_no_ip *common; memset(&values, 0, sizeof(struct extension_values)); pos += sizeof(struct nhrp_fixed_h); common = (struct nhrp_common_h_no_ip *)(buff + pos); sequence_nmbr = ntohl(common->request_ID); if(memcmp(common->src_nbma_address,mpc_control.MPS_CTRL_ATM_ADDR,ATM_ESA_LEN)){ printf("mpcd: p_recogn.c: new MPS! \n" ); return -1; } if(ntohs(fixed->ar_extoff)){ parse_extensions(buff + ntohs(fixed->ar_extoff),&values); } /* if extensions were missing sequence_nmbr == 0 => MPS Death */ keep_alive_sm(values.keep_alive_lifetime, sequence_nmbr); return 1; }
static int doit(const char *filename, int mergep) { krb5_error_code ret; FILE *f; char s[8192]; /* XXX should fix this properly */ char *p; int line; int flags = O_RDWR; struct entry e; hdb_entry_ex ent; HDB *db = _kadm5_s_get_db(kadm_handle); f = fopen(filename, "r"); if(f == NULL){ krb5_warn(context, errno, "fopen(%s)", filename); return 1; } ret = kadm5_log_truncate (kadm_handle); if (ret) { fclose (f); krb5_warn(context, ret, "kadm5_log_truncate"); return 1; } if(!mergep) flags |= O_CREAT | O_TRUNC; ret = db->hdb_open(context, db, flags, 0600); if(ret){ krb5_warn(context, ret, "hdb_open"); fclose(f); return 1; } line = 0; ret = 0; while(fgets(s, sizeof(s), f) != NULL) { ret = 0; line++; p = s; while (isspace((unsigned char)*p)) p++; e.principal = p; for(p = s; *p; p++){ if(*p == '\\') p++; else if(isspace((unsigned char)*p)) { *p = 0; break; } } p = skip_next(p); e.key = p; p = skip_next(p); e.created = p; p = skip_next(p); e.modified = p; p = skip_next(p); e.valid_start = p; p = skip_next(p); e.valid_end = p; p = skip_next(p); e.pw_end = p; p = skip_next(p); e.max_life = p; p = skip_next(p); e.max_renew = p; p = skip_next(p); e.flags = p; p = skip_next(p); e.generation = p; p = skip_next(p); e.extensions = p; p = skip_next(p); memset(&ent, 0, sizeof(ent)); ret = krb5_parse_name(context, e.principal, &ent.entry.principal); if(ret) { fprintf(stderr, "%s:%d:%s (%s)\n", filename, line, krb5_get_err_text(context, ret), e.principal); continue; } if (parse_keys(&ent.entry, e.key)) { fprintf (stderr, "%s:%d:error parsing keys (%s)\n", filename, line, e.key); hdb_free_entry (context, &ent); continue; } if (parse_event(&ent.entry.created_by, e.created) == -1) { fprintf (stderr, "%s:%d:error parsing created event (%s)\n", filename, line, e.created); hdb_free_entry (context, &ent); continue; } if (parse_event_alloc (&ent.entry.modified_by, e.modified) == -1) { fprintf (stderr, "%s:%d:error parsing event (%s)\n", filename, line, e.modified); hdb_free_entry (context, &ent); continue; } if (parse_time_string_alloc (&ent.entry.valid_start, e.valid_start) == -1) { fprintf (stderr, "%s:%d:error parsing time (%s)\n", filename, line, e.valid_start); hdb_free_entry (context, &ent); continue; } if (parse_time_string_alloc (&ent.entry.valid_end, e.valid_end) == -1) { fprintf (stderr, "%s:%d:error parsing time (%s)\n", filename, line, e.valid_end); hdb_free_entry (context, &ent); continue; } if (parse_time_string_alloc (&ent.entry.pw_end, e.pw_end) == -1) { fprintf (stderr, "%s:%d:error parsing time (%s)\n", filename, line, e.pw_end); hdb_free_entry (context, &ent); continue; } if (parse_integer_alloc (&ent.entry.max_life, e.max_life) == -1) { fprintf (stderr, "%s:%d:error parsing lifetime (%s)\n", filename, line, e.max_life); hdb_free_entry (context, &ent); continue; } if (parse_integer_alloc (&ent.entry.max_renew, e.max_renew) == -1) { fprintf (stderr, "%s:%d:error parsing lifetime (%s)\n", filename, line, e.max_renew); hdb_free_entry (context, &ent); continue; } if (parse_hdbflags2int (&ent.entry.flags, e.flags) != 1) { fprintf (stderr, "%s:%d:error parsing flags (%s)\n", filename, line, e.flags); hdb_free_entry (context, &ent); continue; } if(parse_generation(e.generation, &ent.entry.generation) == -1) { fprintf (stderr, "%s:%d:error parsing generation (%s)\n", filename, line, e.generation); hdb_free_entry (context, &ent); continue; } if(parse_extensions(e.extensions, &ent.entry.extensions) == -1) { fprintf (stderr, "%s:%d:error parsing extension (%s)\n", filename, line, e.extensions); hdb_free_entry (context, &ent); continue; } ret = db->hdb_store(context, db, HDB_F_REPLACE, &ent); hdb_free_entry (context, &ent); if (ret) { krb5_warn(context, ret, "db_store"); break; } } db->hdb_close(context, db); fclose(f); return ret != 0; }
void resource_manager::process_file(int rank, FILE *fp, const char *filename, FILE *outfp) { // If none of these comments appear in the header section, and we are // just analyzing the file (ie outfp is 0), then we can return immediately. static const char *header_comment_table[] = { "DocumentNeededResources:", "DocumentSuppliedResources:", "DocumentNeededFonts:", "DocumentSuppliedFonts:", "DocumentNeededProcSets:", "DocumentSuppliedProcSets:", "DocumentNeededFiles:", "DocumentSuppliedFiles:", }; const int NHEADER_COMMENTS = sizeof(header_comment_table) / sizeof(header_comment_table[0]); struct comment_info { const char *name; int (resource_manager::*proc)(const char *, int, FILE *, FILE *); }; static comment_info comment_table[] = { { "BeginResource:", &resource_manager::do_begin_resource }, { "IncludeResource:", &resource_manager::do_include_resource }, { "BeginDocument:", &resource_manager::do_begin_document }, { "IncludeDocument:", &resource_manager::do_include_document }, { "BeginProcSet:", &resource_manager::do_begin_procset }, { "IncludeProcSet:", &resource_manager::do_include_procset }, { "BeginFont:", &resource_manager::do_begin_font }, { "IncludeFont:", &resource_manager::do_include_font }, { "BeginFile:", &resource_manager::do_begin_file }, { "IncludeFile:", &resource_manager::do_include_file }, { "EndProcSet", &resource_manager::change_to_end_resource }, { "EndFont", &resource_manager::change_to_end_resource }, { "EndFile", &resource_manager::change_to_end_resource }, { "BeginPreview:", &resource_manager::do_begin_preview }, { "BeginData:", &resource_manager::do_begin_data }, { "BeginBinary:", &resource_manager::do_begin_binary }, }; const int NCOMMENTS = sizeof(comment_table)/sizeof(comment_table[0]); string buf; int saved_lineno = current_lineno; const char *saved_filename = current_filename; current_filename = filename; current_lineno = 0; if (!ps_get_line(buf, fp)) { current_filename = saved_filename; current_lineno = saved_lineno; return; } if ((size_t)buf.length() < sizeof(PS_MAGIC) || memcmp(buf.contents(), PS_MAGIC, sizeof(PS_MAGIC) - 1) != 0) { if (outfp) { do { if (!(broken_flags & STRIP_PERCENT_BANG) || buf[0] != '%' || buf[1] != '!') fputs(buf.contents(), outfp); } while (ps_get_line(buf, fp)); } } else { if (!(broken_flags & STRIP_PERCENT_BANG) && outfp) fputs(buf.contents(), outfp); int in_header = 1; int interesting = 0; int had_extensions_comment = 0; int had_language_level_comment = 0; for (;;) { if (!ps_get_line(buf, fp)) break; int copy_this_line = 1; if (buf[0] == '%') { if (buf[1] == '%') { const char *ptr; int i; for (i = 0; i < NCOMMENTS; i++) if ((ptr = matches_comment(buf, comment_table[i].name))) { copy_this_line = (this->*(comment_table[i].proc))(ptr, rank, fp, outfp); break; } if (i >= NCOMMENTS && in_header) { if ((ptr = matches_comment(buf, "EndComments"))) in_header = 0; else if (!had_extensions_comment && (ptr = matches_comment(buf, "Extensions:"))) { extensions |= parse_extensions(ptr); // XXX handle possibility that next line is %%+ had_extensions_comment = 1; } else if (!had_language_level_comment && (ptr = matches_comment(buf, "LanguageLevel:"))) { unsigned ll; if (read_uint_arg(&ptr, &ll) && ll > language_level) language_level = ll; had_language_level_comment = 1; } else { for (i = 0; i < NHEADER_COMMENTS; i++) if (matches_comment(buf, header_comment_table[i])) { interesting = 1; break; } } } if ((broken_flags & STRIP_STRUCTURE_COMMENTS) && (matches_comment(buf, "EndProlog") || matches_comment(buf, "Page:") || matches_comment(buf, "Trailer"))) copy_this_line = 0; } else if (buf[1] == '!') { if (broken_flags & STRIP_PERCENT_BANG) copy_this_line = 0; } } else in_header = 0; if (!outfp && !in_header && !interesting) break; if (copy_this_line && outfp) fputs(buf.contents(), outfp); } } current_filename = saved_filename; current_lineno = saved_lineno; }
/* Parse a TLS packet for the Server Name Indication extension in the client * hello handshake, returning the first servername found (pointer to static * array) * * Returns: * >=0 - length of the hostname and updates *hostname * caller is responsible for freeing *hostname * -1 - Incomplete request * -2 - No Host header included in this request * -3 - Invalid hostname pointer * -4 - malloc failure * < -4 - Invalid TLS client hello */ static int parse_tls_header(const char *data, size_t data_len, char **hostname) { char tls_content_type; char tls_version_major; char tls_version_minor; size_t pos = TLS_HEADER_LEN; size_t len; if (hostname == NULL) return -3; /* Check that our TCP payload is at least large enough for a TLS header */ if (data_len < TLS_HEADER_LEN) return -1; tls_content_type = data[0]; if (tls_content_type != TLS_HANDSHAKE_CONTENT_TYPE) { debug("Request did not begin with TLS handshake."); return -5; } tls_version_major = data[1]; tls_version_minor = data[2]; if (tls_version_major < 3) { debug("Received SSL %d.%d handshake which cannot be parsed.", tls_version_major, tls_version_minor); return -2; } /* TLS record length */ len = ((unsigned char)data[3] << 8) + (unsigned char)data[4] + TLS_HEADER_LEN; data_len = MIN(data_len, len); /* Check we received entire TLS record length */ if (data_len < len) return -1; /* * Handshake */ if (pos + 1 > data_len) { return -5; } if (data[pos] != TLS_HANDSHAKE_TYPE_CLIENT_HELLO) { debug("Not a client hello"); return -5; } /* Skip past fixed length records: 1 Handshake Type 3 Length 2 Version (again) 32 Random to Session ID Length */ pos += 38; /* Session ID */ if (pos + 1 > data_len) return -5; len = (unsigned char)data[pos]; pos += 1 + len; /* Cipher Suites */ if (pos + 2 > data_len) return -5; len = ((unsigned char)data[pos] << 8) + (unsigned char)data[pos + 1]; pos += 2 + len; /* Compression Methods */ if (pos + 1 > data_len) return -5; len = (unsigned char)data[pos]; pos += 1 + len; if (pos == data_len && tls_version_major == 3 && tls_version_minor == 0) { debug("Received SSL 3.0 handshake without extensions"); return -2; } /* Extensions */ if (pos + 2 > data_len) return -5; len = ((unsigned char)data[pos] << 8) + (unsigned char)data[pos + 1]; pos += 2; if (pos + len > data_len) return -5; return parse_extensions(data + pos, len, hostname); }
static int doit(const char *filename, int mergep) { krb5_error_code ret = 0; FILE *f; char s[8192]; /* XXX should fix this properly */ char *p; int line; int flags = O_RDWR; struct entry e; hdb_entry_ex ent; HDB *db = _kadm5_s_get_db(kadm_handle); f = fopen(filename, "r"); if(f == NULL){ krb5_warn(context, errno, "fopen(%s)", filename); return 1; } /* * We don't have a version number in the dump, so we don't know which iprop * log entries to keep, if any. We throw the log away. * * We could merge the ipropd-master/slave dump/load here as an option, in * which case we would first load the dump. * * If we're merging, first recover unconfirmed records in the existing log. */ if (mergep) ret = kadm5_log_init(kadm_handle); if (ret == 0) ret = kadm5_log_reinit(kadm_handle, 0); if (ret) { fclose (f); krb5_warn(context, ret, "kadm5_log_reinit"); return 1; } if(!mergep) flags |= O_CREAT | O_TRUNC; ret = db->hdb_open(context, db, flags, 0600); if(ret){ krb5_warn(context, ret, "hdb_open"); fclose(f); return 1; } line = 0; ret = 0; while(fgets(s, sizeof(s), f) != NULL) { line++; p = s; while (isspace((unsigned char)*p)) p++; e.principal = p; for(p = s; *p; p++){ if(*p == '\\') p++; else if(isspace((unsigned char)*p)) { *p = 0; break; } } p = skip_next(p); e.key = p; p = skip_next(p); e.created = p; p = skip_next(p); e.modified = p; p = skip_next(p); e.valid_start = p; p = skip_next(p); e.valid_end = p; p = skip_next(p); e.pw_end = p; p = skip_next(p); e.max_life = p; p = skip_next(p); e.max_renew = p; p = skip_next(p); e.flags = p; p = skip_next(p); e.generation = p; p = skip_next(p); e.extensions = p; skip_next(p); memset(&ent, 0, sizeof(ent)); ret = krb5_parse_name(context, e.principal, &ent.entry.principal); if(ret) { const char *msg = krb5_get_error_message(context, ret); fprintf(stderr, "%s:%d:%s (%s)\n", filename, line, msg, e.principal); krb5_free_error_message(context, msg); continue; } if (parse_keys(&ent.entry, e.key)) { fprintf (stderr, "%s:%d:error parsing keys (%s)\n", filename, line, e.key); hdb_free_entry (context, &ent); continue; } if (parse_event(&ent.entry.created_by, e.created) == -1) { fprintf (stderr, "%s:%d:error parsing created event (%s)\n", filename, line, e.created); hdb_free_entry (context, &ent); continue; } if (parse_event_alloc (&ent.entry.modified_by, e.modified) == -1) { fprintf (stderr, "%s:%d:error parsing event (%s)\n", filename, line, e.modified); hdb_free_entry (context, &ent); continue; } if (parse_time_string_alloc (&ent.entry.valid_start, e.valid_start) == -1) { fprintf (stderr, "%s:%d:error parsing time (%s)\n", filename, line, e.valid_start); hdb_free_entry (context, &ent); continue; } if (parse_time_string_alloc (&ent.entry.valid_end, e.valid_end) == -1) { fprintf (stderr, "%s:%d:error parsing time (%s)\n", filename, line, e.valid_end); hdb_free_entry (context, &ent); continue; } if (parse_time_string_alloc (&ent.entry.pw_end, e.pw_end) == -1) { fprintf (stderr, "%s:%d:error parsing time (%s)\n", filename, line, e.pw_end); hdb_free_entry (context, &ent); continue; } if (parse_integer_alloc (&ent.entry.max_life, e.max_life) == -1) { fprintf (stderr, "%s:%d:error parsing lifetime (%s)\n", filename, line, e.max_life); hdb_free_entry (context, &ent); continue; } if (parse_integer_alloc (&ent.entry.max_renew, e.max_renew) == -1) { fprintf (stderr, "%s:%d:error parsing lifetime (%s)\n", filename, line, e.max_renew); hdb_free_entry (context, &ent); continue; } if (parse_hdbflags2int (&ent.entry.flags, e.flags) != 1) { fprintf (stderr, "%s:%d:error parsing flags (%s)\n", filename, line, e.flags); hdb_free_entry (context, &ent); continue; } if(parse_generation(e.generation, &ent.entry.generation) == -1) { fprintf (stderr, "%s:%d:error parsing generation (%s)\n", filename, line, e.generation); hdb_free_entry (context, &ent); continue; } if(parse_extensions(e.extensions, &ent.entry.extensions) == -1) { fprintf (stderr, "%s:%d:error parsing extension (%s)\n", filename, line, e.extensions); hdb_free_entry (context, &ent); continue; } ret = db->hdb_store(context, db, HDB_F_REPLACE, &ent); hdb_free_entry (context, &ent); if (ret) { krb5_warn(context, ret, "db_store"); break; } } (void) kadm5_log_end(kadm_handle); db->hdb_close(context, db); fclose(f); return ret != 0; }
HIDDEN int ws_start_channel(struct transaction_t *txn, const char *protocol, int (*data_cb)(struct buf *inbuf, struct buf *outbuf, struct buf *logbuf, void **rock)) { int r; const char **hdr, *accept = NULL; wslay_event_context_ptr ev; struct ws_context *ctx; struct wslay_event_callbacks callbacks = { recv_cb, send_cb, NULL, NULL, NULL, NULL, on_msg_recv_cb }; /* Check for supported WebSocket version */ hdr = spool_getheader(txn->req_hdrs, "Sec-WebSocket-Version"); if (!hdr) { txn->error.desc = "Missing WebSocket version"; return HTTP_BAD_REQUEST; } else if (hdr[1]) { txn->error.desc = "Multiple WebSocket versions"; return HTTP_BAD_REQUEST; } else if (strcmp(hdr[0], WS_VERSION)) { txn->error.desc = "Unsupported WebSocket version"; return HTTP_UPGRADE; } if (protocol) { /* Check for supported WebSocket subprotocol */ int i, found = 0; hdr = spool_getheader(txn->req_hdrs, "Sec-WebSocket-Protocol"); if (!hdr) { txn->error.desc = "Missing WebSocket protocol"; return HTTP_BAD_REQUEST; } for (i = 0; !found && hdr[i]; i++) { tok_t tok = TOK_INITIALIZER(hdr[i], ",", TOK_TRIMLEFT|TOK_TRIMRIGHT); char *token; while ((token = tok_next(&tok))) { if (!strcmp(token, protocol)) { found = 1; break; } } tok_fini(&tok); } if (!found) { txn->error.desc = "Unsupported WebSocket protocol"; return HTTP_BAD_REQUEST; } } if (txn->flags.ver == VER_1_1) { unsigned char sha1buf[SHA1_DIGEST_LENGTH]; /* Check for WebSocket client key */ hdr = spool_getheader(txn->req_hdrs, "Sec-WebSocket-Key"); if (!hdr) { txn->error.desc = "Missing WebSocket client key"; return HTTP_BAD_REQUEST; } else if (hdr[1]) { txn->error.desc = "Multiple WebSocket client keys"; return HTTP_BAD_REQUEST; } else if (strlen(hdr[0]) != WS_CKEY_LEN) { txn->error.desc = "Invalid WebSocket client key"; return HTTP_BAD_REQUEST; } /* Create WebSocket accept key */ buf_setcstr(&txn->buf, hdr[0]); buf_appendcstr(&txn->buf, WS_GUID); xsha1((u_char *) buf_base(&txn->buf), buf_len(&txn->buf), sha1buf); buf_ensure(&txn->buf, WS_AKEY_LEN+1); accept = buf_base(&txn->buf); r = sasl_encode64((char *) sha1buf, SHA1_DIGEST_LENGTH, (char *) accept, WS_AKEY_LEN+1, NULL); if (r != SASL_OK) syslog(LOG_WARNING, "sasl_encode64: %d", r); } /* Create server context */ r = wslay_event_context_server_init(&ev, &callbacks, txn); if (r) { syslog(LOG_WARNING, "wslay_event_context_init: %s", wslay_strerror(r)); return HTTP_SERVER_ERROR; } /* Create channel context */ ctx = xzmalloc(sizeof(struct ws_context)); ctx->event = ev; ctx->accept = accept; ctx->protocol = protocol; ctx->data_cb = data_cb; txn->ws_ctx = ctx; /* Check for supported WebSocket extensions */ parse_extensions(txn); /* Prepare log buffer */ /* Add client data */ buf_printf(&ctx->log, "%s", txn->conn->clienthost); if (httpd_userid) buf_printf(&ctx->log, " as \"%s\"", httpd_userid); if ((hdr = spool_getheader(txn->req_hdrs, "User-Agent"))) { buf_printf(&ctx->log, " with \"%s\"", hdr[0]); if ((hdr = spool_getheader(txn->req_hdrs, "X-Client"))) buf_printf(&ctx->log, " by \"%s\"", hdr[0]); else if ((hdr = spool_getheader(txn->req_hdrs, "X-Requested-With"))) buf_printf(&ctx->log, " by \"%s\"", hdr[0]); } /* Add request-line */ buf_printf(&ctx->log, "; \"WebSocket/%s via %s\"", protocol ? protocol : "echo" , txn->req_line.ver); ctx->log_tail = buf_len(&ctx->log); /* Tell client that WebSocket negotiation has succeeded */ if (txn->conn->sess_ctx) { /* Treat WS data as chunked response */ txn->flags.te = TE_CHUNKED; response_header(HTTP_OK, txn); /* Force the response to the client immediately */ prot_flush(httpd_out); } else response_header(HTTP_SWITCH_PROT, txn); /* Set connection as non-blocking */ prot_NONBLOCK(txn->conn->pin); /* Don't do telemetry logging in prot layer */ prot_setlog(txn->conn->pin, PROT_NO_FD); prot_setlog(txn->conn->pout, PROT_NO_FD); return 0; }