void Http2Base::PingProc(const Http2_header* header) { if((header->flags & ACK_F) == 0) { Http2_header *header_back = (Http2_header *)p_memdup(header, sizeof(Http2_header) + get24(header->length)); header_back->flags |= ACK_F; PushFrame(header_back); } }
static char * p_strarray_join_n(pool_t pool, const char *const *arr, unsigned int arr_len, const char *separator) { size_t alloc_len, sep_len, len, pos, needed_space; unsigned int i; char *str; sep_len = strlen(separator); alloc_len = 64; str = t_buffer_get(alloc_len); pos = 0; for (i = 0; i < arr_len; i++) { len = strlen(arr[i]); needed_space = pos + len + sep_len + 1; if (needed_space > alloc_len) { alloc_len = nearest_power(needed_space); str = t_buffer_reget(str, alloc_len); } if (pos != 0) { memcpy(str + pos, separator, sep_len); pos += sep_len; } memcpy(str + pos, arr[i], len); pos += len; } str[pos] = '\0'; if (!pool->datastack_pool) return p_memdup(pool, str, pos + 1); t_buffer_alloc(pos + 1); return str; }
void Http2Base::SettingsProc(const Http2_header* header) { const Setting_Frame *sf = (const Setting_Frame *)(header + 1); if((header->flags & ACK_F) == 0) { while((char *)sf-(char *)(header+1) < get24(header->length)){ uint32_t value = get32(sf->value); switch(get16(sf->identifier)){ case SETTINGS_HEADER_TABLE_SIZE: LOGD(DHTTP2, "set head table size:%d\n", value); request_table.set_dynamic_table_size_limit_max(value); break; case SETTINGS_INITIAL_WINDOW_SIZE: if(value >= (uint32_t)1<<31u){ LOGE("ERROR window overflow\n"); ErrProc(ERR_FLOW_CONTROL_ERROR); return; } AdjustInitalFrameWindowSize((ssize_t)value - (ssize_t)remoteframewindowsize); remoteframewindowsize = value; LOGD(DHTTP2, "set inital frame window size:%d\n", remoteframewindowsize); break; case SETTINGS_MAX_FRAME_SIZE: if(value > 0xffffff || value < FRAMEBODYLIMIT){ LOGE("ERROR frame size overflow\n"); ErrProc(ERR_FRAME_SIZE_ERROR); return; } remoteframebodylimit = value; LOGD(DHTTP2, "set frame body size limit: %d\n", remoteframebodylimit); break; default: LOG("Get a unkown setting(%d): %d\n", get16(sf->identifier), value); break; } sf++; } Http2_header *header_back = (Http2_header *)p_memdup(header, sizeof(Http2_header)); set24(header_back->length, 0); header_back->flags |= ACK_F; PushFrame(header_back); }else if(get24(header->length) != 0){ LOGE("ERROR setting ack with content\n"); ErrProc(ERR_FRAME_SIZE_ERROR); } }
static int master_service_haproxy_parse_tlv(struct master_service_haproxy_conn *hpconn, const unsigned char *buf, size_t blen, const char **error_r) { for(size_t i = 0; i < blen;) { struct haproxy_pp2_tlv kv; struct haproxy_pp2_tlv_ssl ssl_kv; if (get_tlv(buf + i, blen - i, &kv) < 0) { *error_r = t_strdup_printf("get_tlv(%"PRIuSIZE_T") failed:" "Truncated data", i); return -1; } /* skip unsupported values */ switch(kv.type) { case PP2_TYPE_ALPN: hpconn->conn.proxy.alpn_size = kv.len; hpconn->conn.proxy.alpn = p_memdup(hpconn->pool, kv.data, kv.len); break; case PP2_TYPE_AUTHORITY: /* store hostname somewhere */ hpconn->conn.proxy.hostname = p_strndup(hpconn->pool, kv.data, kv.len); break; case PP2_TYPE_SSL: if (get_ssl_tlv(kv.data, kv.len, &ssl_kv) < 0) { *error_r = t_strdup_printf("get_ssl_tlv(%"PRIuSIZE_T") failed:" "Truncated data", i); return -1; } if (master_service_haproxy_parse_ssl_tlv(hpconn, &ssl_kv, error_r)<0) return -1; break; } i += SIZEOF_PP2_TLV + kv.len; } return 0; }