int moloch_field_define(char *group, char *kind, char *expression, char *friendlyName, char *dbField, char *help, int type, int flags, ...) { char dbField2[100]; char expression2[1000]; char friendlyName2[1000]; char help2[1000]; char rawField[100]; MolochFieldInfo_t *minfo = 0; HASH_FIND(f_, fields, dbField, minfo); if (!minfo) { minfo = MOLOCH_TYPE_ALLOC0(MolochFieldInfo_t); minfo->dbFieldMem = g_strdup(dbField); minfo->dbField = minfo->dbFieldMem; minfo->dbFieldLen = strlen(minfo->dbField); minfo->pos = -1; minfo->expression = g_strdup(expression); minfo->group = g_strdup(group); HASH_ADD(f_, fields, minfo->dbField, minfo); if ((flags & MOLOCH_FIELD_FLAG_NODB) == 0) { va_list args; va_start(args, flags); moloch_db_add_field(group, kind, expression, friendlyName, dbField, help, args); va_end(args); } } // Hack to remove trailing .snow on capture side int dbLen = strlen(minfo->dbField); if (dbLen > 5 && memcmp(".snow", minfo->dbField+dbLen-5, 5) == 0) { minfo->dbField[dbLen-5] = 0; minfo->dbFieldLen -= 5; } minfo->type = type; minfo->flags = flags; if ((flags & MOLOCH_FIELD_FLAG_FAKE) == 0) { if (minfo->pos == -1) { minfo->pos = config.maxField++; } config.fields[minfo->pos] = minfo; // Change leading part to dbGroup char *firstdot = strchr(minfo->dbField, '.'); if (firstdot) { static char lastGroup[100] = ""; static int groupNum = 0; if (memcmp(minfo->dbField, lastGroup, (firstdot-minfo->dbField)+1) == 0) { minfo->dbGroupNum = groupNum; } else { groupNum++; minfo->dbGroupNum = groupNum; memcpy(lastGroup, minfo->dbField, (firstdot-minfo->dbField)+1); } minfo->dbGroup = minfo->dbField; minfo->dbGroupLen = firstdot - minfo->dbField; minfo->dbField += (firstdot - minfo->dbField) + 1; minfo->dbFieldLen = strlen(minfo->dbField); } } if (flags & MOLOCH_FIELD_FLAG_NODB) return minfo->pos; MolochFieldInfo_t *info = 0; if (flags & MOLOCH_FIELD_FLAG_CNT) { sprintf(dbField2, "%scnt", dbField); HASH_FIND(f_, fields, dbField2, info); if (!info) { sprintf(expression2, "%s.cnt", expression); sprintf(friendlyName2, "%s Cnt", friendlyName); sprintf(help2, "Unique number of %s", help); moloch_db_add_field(group, "integer", expression2, friendlyName2, dbField2, help2, NULL); } } if (flags & MOLOCH_FIELD_FLAG_SCNT) { sprintf(dbField2, "%sscnt", dbField); HASH_FIND(f_, fields, dbField2, info); if (!info) { sprintf(expression2, "%s.cnt", expression); sprintf(friendlyName2, "%s Cnt", friendlyName); sprintf(help2, "Unique number of %s", help); moloch_db_add_field(group, "integer", expression2, friendlyName2, dbField2, help2, NULL); } } if (flags & MOLOCH_FIELD_FLAG_COUNT) { sprintf(dbField2, "%s-cnt", dbField); HASH_FIND(f_, fields, dbField2, info); if (!info) { sprintf(expression2, "%s.cnt", expression); sprintf(friendlyName2, "%s Cnt", friendlyName); sprintf(help2, "Unique number of %s", help); moloch_db_add_field(group, "integer", expression2, friendlyName2, dbField2, help2, NULL); } } if (flags & MOLOCH_FIELD_FLAG_FAKE) { g_free(minfo->expression); g_free(minfo->dbField); g_free(minfo->group); HASH_REMOVE(f_, fields, minfo); MOLOCH_TYPE_FREE(MolochFieldInfo_t, minfo); return -1; } if (flags & MOLOCH_FIELD_FLAG_IPPRE) { int fnlen = strlen(friendlyName); sprintf(dbField2, "g%s", dbField); HASH_FIND(f_, fields, dbField2, info); if (!info) { sprintf(expression2, "country.%s", expression+3); sprintf(friendlyName2, "%.*s GEO", fnlen-2, friendlyName); sprintf(help2, "GeoIP country string calculated from the %s", help); moloch_db_add_field(group, "uptermfield", expression2, friendlyName2, dbField2, help2, NULL); } sprintf(dbField2, "as%s", dbField); HASH_FIND(f_, fields, dbField2, info); if (!info) { sprintf(expression2, "asn.%s", expression+3); sprintf(friendlyName2, "%.*s ASN", fnlen-2, friendlyName); sprintf(help2, "GeoIP ASN string calculated from the %s", help); sprintf(rawField, "raw%s", dbField2); moloch_nids_add_field_proxy(group, "textfield", expression2, friendlyName2, dbField2, help2, "rawField", rawField, NULL); } sprintf(dbField2, "rir%s", dbField); HASH_FIND(f_, fields, dbField2, info); if (!info) { sprintf(expression2, "rir.%s", expression+3); sprintf(friendlyName2, "%.*s RIR", fnlen-2, friendlyName); sprintf(help2, "Regional Internet Registry string calculated from %s", help); moloch_db_add_field(group, "uptermfield", expression2, friendlyName2, dbField2, help2, NULL); } } else if (type == MOLOCH_FIELD_TYPE_IP || type == MOLOCH_FIELD_TYPE_IP_HASH) { sprintf(dbField2, "%s-geo", dbField); HASH_FIND(f_, fields, dbField2, info); if (!info) { sprintf(expression2, "%s.country", expression); sprintf(friendlyName2, "%s GEO", friendlyName); sprintf(help2, "GeoIP country string calculated from the %s", help); moloch_db_add_field(group, "uptermfield", expression2, friendlyName2, dbField2, help2, NULL); } sprintf(dbField2, "%s-asn.snow", dbField); HASH_FIND(f_, fields, dbField2, info); if (!info) { sprintf(dbField2, "%s-asn.snow", dbField); sprintf(expression2, "%s.asn", expression); sprintf(friendlyName2, "%s ASN", friendlyName); sprintf(rawField, "%s-asn.raw", dbField); sprintf(help2, "GeoIP ASN string calculated from the %s", help); moloch_nids_add_field_proxy(group, "textfield", expression2, friendlyName2, dbField2, help2, "rawField", rawField, NULL); } sprintf(dbField2, "%s-rir", dbField); HASH_FIND(f_, fields, dbField2, info); if (!info) { sprintf(expression2, "%s.rir", expression); sprintf(friendlyName2, "%s RIR", friendlyName); sprintf(help2, "Regional Internet Registry string calculated from %s", help); moloch_db_add_field(group, "uptermfield", expression2, friendlyName2, dbField2, help2, NULL); } } return minfo->pos; }
int moloch_http_connect(MolochConn_t *conn, char *name, int defaultport, int blocking) { GError *error = 0; GSocketConnectable *connectable; GSocketAddressEnumerator *enumerator; GSocketAddress *sockaddr; struct timeval startTime; struct timeval stopTime; gettimeofday(&startTime, NULL); connectable = g_network_address_parse(name, defaultport, &error); if (error) { LOG("%p: Couldn't parse connect string of %s", (void*)conn, name); exit(0); } conn->name = name; enumerator = g_socket_connectable_enumerate (connectable); g_object_unref(connectable); while (!conn->conn && (sockaddr = g_socket_address_enumerator_next (enumerator, NULL, &error))) { conn->conn = g_socket_new(G_SOCKET_FAMILY_IPV4, G_SOCKET_TYPE_STREAM, G_SOCKET_PROTOCOL_TCP, &error); if (!error) { GValue value = G_VALUE_INIT; g_value_init (&value, G_TYPE_BOOLEAN); g_value_set_boolean (&value, blocking); g_object_set_property(G_OBJECT(conn->conn), "blocking", &value); g_socket_connect(conn->conn, sockaddr, NULL, &error); } if (error && error->code != G_IO_ERROR_PENDING) { g_object_unref (conn->conn); conn->conn = NULL; } else { struct sockaddr_in localAddress, remoteAddress; socklen_t addressLength = sizeof(localAddress); getsockname(g_socket_get_fd(conn->conn), (struct sockaddr*)&localAddress, &addressLength); g_socket_address_to_native(sockaddr, &remoteAddress, addressLength, NULL); char sessionId[MOLOCH_SESSIONID_LEN]; moloch_session_id(sessionId, localAddress.sin_addr.s_addr, localAddress.sin_port, remoteAddress.sin_addr.s_addr, remoteAddress.sin_port); DEBUGCONN("AAA connected %s %p %s", conn->server->names[0], conn, moloch_friendly_session_id(17, localAddress.sin_addr.s_addr, htons(localAddress.sin_port), remoteAddress.sin_addr.s_addr, htons(remoteAddress.sin_port))); HASH_ADD(h_, connections, sessionId, conn); memcpy(&conn->sessionIda, sessionId, 8); memcpy(&conn->sessionIdb, sessionId+8, 4); conn->server->numConns++; } g_object_unref (sockaddr); } g_object_unref (enumerator); if (conn->conn) { if (error) { g_error_free(error); error = 0; } } else if (error) { LOG("%p: Error: %s", (void*)conn, error->message); } if (error || !conn->conn) { if (config.logESRequests) LOG("Connecting %p %s %d %d FAIL", (void*)conn, name, defaultport, blocking); conn->server->lastFailedConnect = time(0); return 1; } //g_object_ref (conn->conn); g_socket_set_keepalive(conn->conn, TRUE); int fd = g_socket_get_fd(conn->conn); conn->readWatch = moloch_watch_fd(fd, MOLOCH_GIO_READ_COND, moloch_http_read_cb, conn); if (!blocking) { conn->writeWatch = moloch_watch_fd(fd, G_IO_OUT, moloch_http_conn_cb, conn); DEBUGCONN("AAA connwritewatch %s %p fd:%d ww:%d", conn->server->names[0], conn, fd, conn->writeWatch); } int sendbuff = 0; socklen_t optlen = sizeof(sendbuff); int res = getsockopt(fd, SOL_SOCKET, SO_SNDBUF, &sendbuff, &optlen); if(res != -1 && sendbuff < 300000) { sendbuff = 300000; setsockopt(fd, SOL_SOCKET, SO_SNDBUF, &sendbuff, sizeof(sendbuff)); } #ifdef TCP_KEEPIDLE res = getsockopt(fd, IPPROTO_TCP, TCP_KEEPIDLE, &sendbuff, &optlen); if(res != -1 && sendbuff > 60*8) { sendbuff = 60*8; setsockopt(fd, IPPROTO_TCP, TCP_KEEPIDLE, &sendbuff, sizeof(sendbuff)); } #endif gettimeofday(&stopTime, NULL); if (config.logESRequests) LOG("Connecting %p %s %d %d %ldms", (void*)conn, name, defaultport, blocking, (stopTime.tv_sec - startTime.tv_sec)*1000 + (stopTime.tv_usec - startTime.tv_usec)/1000); return 0; }
void AddWidgetToViewHandle(ViewHandle * MainViewHandle, const char * NewName, GtkWidget * NewWidget){ ObjectHandle * NewObject; NewObject = ObjectHandle_Initialize(NewName, NewWidget, MainViewHandle); HASH_ADD(HashByName, MainViewHandle->ObjectListByName, Name, sizeof(char) * MAX_HASH_KEY_LENGTH, NewObject); HASH_ADD(HashByWidget,MainViewHandle->ObjectListByWidget,Widget,sizeof(GtkWidget *),NewObject); }
void draw_character(SDL_Renderer *screen,int x,int y,int w,uint32_t cin,uint32_t bg,uint32_t fg,int bold,int underline,int italic,int strike) { SDL_Texture *texture=0; lookup_key_t chr; chr.c = cin; chr.fg = fg; chr.bg = bg; chr.bold = bold; chr.underline = underline; chr.italic = italic; chr.strike = strike; char_render_t *mchr=0; HASH_FIND( hh, display_cache, &chr, char_render_t_keylen, mchr); if(!mchr) { /* masks for desired format */ const uint32_t Rmask = 0xff000000; const uint32_t Gmask = 0x00ff0000; const uint32_t Bmask = 0x0000ff00; const uint32_t Amask = 0x000000ff; const int bpp=32; /* bits per pixel for desired format */ // SDL_Surface *converted = SDL_CreateRGBSurface(0,w,16,32,0,0,0,0); SDL_Surface *converted = SDL_CreateRGBSurface(SDL_SWSURFACE, w, 16, bpp, Rmask, Gmask, Bmask, Amask); if(converted == NULL) { printf("failed to create surface\n"); } draw_character_surface(converted,0,0,w,cin,bg,fg,bold,underline,italic,strike); // texture = SDL_CreateTexture(screen,converted->format,0,w,16); // (((uint32_t *) (converted->pixels))[0]) = 0xFFFFFFFF; // SDL_UpdateTexture(texture,NULL,converted->pixels,w*4); texture = SDL_CreateTextureFromSurface(screen, converted); // SDL_Rect dstRect = { x, y, w, 16 }; // SDL_RenderCopy(screen, texture, NULL, &dstRect); // SDL_FreeSurface(converted); mchr = (char_render_t *) malloc(sizeof(char_render_t)); mchr->c = cin; mchr->fg = fg; mchr->bg = bg; mchr->bold = bold; mchr->underline = underline; mchr->italic = italic; mchr->strike = strike; mchr->texture = texture; HASH_ADD( hh, display_cache, c, char_render_t_keylen, mchr); } SDL_Rect dstRect = { x, y, w, 16 }; SDL_RenderCopy(screen, mchr->texture, NULL, &dstRect); }
int moloch_field_define(char *group, char *kind, char *expression, char *friendlyName, char *dbField, char *help, int type, int flags, ...) { char dbField2[100]; char expression2[1000]; char friendlyName2[1000]; char help2[1000]; char rawField[100]; MolochFieldInfo_t *minfo = 0; HASH_FIND(d_, fieldsByDb, dbField, minfo); if (!minfo) { minfo = MOLOCH_TYPE_ALLOC0(MolochFieldInfo_t); minfo->dbFieldFull = g_strdup(dbField); minfo->dbField = minfo->dbFieldFull; minfo->dbFieldLen = strlen(minfo->dbField); minfo->pos = -1; minfo->expression = g_strdup(expression); minfo->group = g_strdup(group); minfo->kind = g_strdup(kind); HASH_ADD(d_, fieldsByDb, minfo->dbField, minfo); HASH_ADD(e_, fieldsByExp, minfo->expression, minfo); if ((flags & MOLOCH_FIELD_FLAG_NODB) == 0) { va_list args; va_start(args, flags); moloch_db_add_field(group, kind, expression, friendlyName, dbField, help, TRUE, args); va_end(args); } } else { char *category = NULL; if (strcmp(kind, minfo->kind) != 0) { LOG("WARNING - Field kind in db %s doesn't match field kind %s in capture for field %s", minfo->kind, kind, expression); } va_list args; va_start(args, flags); while(1) { char *field = va_arg(args, char *); if (!field) break; char *value = va_arg(args, char *); if (strcmp(field, "category") == 0 && value) { category = value; } } va_end(args); if (category && (!minfo->category || strcmp(category, minfo->category) != 0)) { LOG("UPDATING - Field category in db %s doesn't match field category %s in capture for field %s", minfo->category, category, expression); moloch_db_update_field(expression, "category", category); } } // Hack to remove trailing .snow on capture side int dbLen = strlen(minfo->dbField); if (dbLen > 5 && memcmp(".snow", minfo->dbField+dbLen-5, 5) == 0) { minfo->dbField[dbLen-5] = 0; minfo->dbFieldLen -= 5; } minfo->type = type; minfo->flags = flags; if ((flags & MOLOCH_FIELD_FLAG_FAKE) == 0) { if (minfo->pos == -1) { minfo->pos = config.maxField++; if (config.maxField > 255) { LOGEXIT("ERROR - Max Fields is too large %d", config.maxField); } } config.fields[minfo->pos] = minfo; // Change leading part to dbGroup char *firstdot = strchr(minfo->dbField, '.'); if (firstdot) { static char lastGroup[100] = ""; static int groupNum = 0; if (memcmp(minfo->dbField, lastGroup, (firstdot-minfo->dbField)+1) == 0) { minfo->dbGroupNum = groupNum; } else { groupNum++; minfo->dbGroupNum = groupNum; memcpy(lastGroup, minfo->dbField, (firstdot-minfo->dbField)+1); } minfo->dbGroup = minfo->dbField; minfo->dbGroupLen = firstdot - minfo->dbField; minfo->dbField += (firstdot - minfo->dbField) + 1; minfo->dbFieldLen = strlen(minfo->dbField); } } if (flags & MOLOCH_FIELD_FLAG_NODB) return minfo->pos; MolochFieldInfo_t *info = 0; if (flags & MOLOCH_FIELD_FLAG_CNT) { snprintf(dbField2, sizeof(dbField2), "%scnt", dbField); HASH_FIND(d_, fieldsByDb, dbField2, info); if (!info) { snprintf(expression2, sizeof(expression2), "%s.cnt", expression); snprintf(friendlyName2, sizeof(friendlyName2), "%s Cnt", friendlyName); snprintf(help2, sizeof(help2), "Unique number of %s", help); moloch_db_add_field(group, "integer", expression2, friendlyName2, dbField2, help2, FALSE, empty_va_list); } } if (flags & MOLOCH_FIELD_FLAG_SCNT) { snprintf(dbField2, sizeof(dbField2), "%sscnt", dbField); HASH_FIND(d_, fieldsByDb, dbField2, info); if (!info) { snprintf(expression2, sizeof(expression2), "%s.cnt", expression); snprintf(friendlyName2, sizeof(friendlyName2), "%s Cnt", friendlyName); snprintf(help2, sizeof(help2), "Unique number of %s", help); moloch_db_add_field(group, "integer", expression2, friendlyName2, dbField2, help2, FALSE, empty_va_list); } } if (flags & MOLOCH_FIELD_FLAG_COUNT) { snprintf(dbField2, sizeof(dbField2), "%s-cnt", dbField); HASH_FIND(d_, fieldsByDb, dbField2, info); if (!info) { snprintf(expression2, sizeof(expression2), "%s.cnt", expression); snprintf(friendlyName2, sizeof(friendlyName2), "%s Cnt", friendlyName); snprintf(help2, sizeof(help2), "Unique number of %s", help); moloch_db_add_field(group, "integer", expression2, friendlyName2, dbField2, help2, FALSE, empty_va_list); } } if (flags & MOLOCH_FIELD_FLAG_FAKE) { g_free(minfo->expression); g_free(minfo->dbField); g_free(minfo->group); g_free(minfo->kind); HASH_REMOVE(d_, fieldsByDb, minfo); HASH_REMOVE(e_, fieldsByExp, minfo); MOLOCH_TYPE_FREE(MolochFieldInfo_t, minfo); return -1; } if (flags & MOLOCH_FIELD_FLAG_IPPRE) { int fnlen = strlen(friendlyName); snprintf(dbField2, sizeof(dbField2), "g%s", dbField); HASH_FIND(d_, fieldsByDb, dbField2, info); if (!info) { snprintf(expression2, sizeof(expression2), "country.%s", expression+3); snprintf(friendlyName2, sizeof(friendlyName2), "%.*s GEO", fnlen-2, friendlyName); snprintf(help2, sizeof(help2), "GeoIP country string calculated from the %s", help); moloch_db_add_field(group, "uptermfield", expression2, friendlyName2, dbField2, help2, FALSE, empty_va_list); } snprintf(dbField2, sizeof(dbField2), "as%s", dbField); HASH_FIND(d_, fieldsByDb, dbField2, info); if (!info) { snprintf(expression2, sizeof(expression2), "asn.%s", expression+3); snprintf(friendlyName2, sizeof(friendlyName2), "%.*s ASN", fnlen-2, friendlyName); snprintf(help2, sizeof(help2), "GeoIP ASN string calculated from the %s", help); snprintf(rawField, sizeof(rawField), "raw%s", dbField2); moloch_session_add_field_proxy(group, "textfield", expression2, friendlyName2, dbField2, help2, "rawField", rawField, NULL); } snprintf(dbField2, sizeof(dbField2), "rir%s", dbField); HASH_FIND(d_, fieldsByDb, dbField2, info); if (!info) { snprintf(expression2, sizeof(expression2), "rir.%s", expression+3); snprintf(friendlyName2, sizeof(friendlyName2), "%.*s RIR", fnlen-2, friendlyName); snprintf(help2, sizeof(help2), "Regional Internet Registry string calculated from %s", help); moloch_db_add_field(group, "uptermfield", expression2, friendlyName2, dbField2, help2, FALSE, empty_va_list); } } else if (type == MOLOCH_FIELD_TYPE_IP || type == MOLOCH_FIELD_TYPE_IP_HASH || type == MOLOCH_FIELD_TYPE_IP_GHASH) { snprintf(dbField2, sizeof(dbField2), "%s-geo", dbField); HASH_FIND(d_, fieldsByDb, dbField2, info); if (!info) { snprintf(expression2, sizeof(expression2), "%s.country", expression); snprintf(friendlyName2, sizeof(friendlyName2), "%s GEO", friendlyName); snprintf(help2, sizeof(help2), "GeoIP country string calculated from the %s", help); moloch_db_add_field(group, "uptermfield", expression2, friendlyName2, dbField2, help2, FALSE, empty_va_list); } snprintf(dbField2, sizeof(dbField2), "%s-asn.snow", dbField); HASH_FIND(d_, fieldsByDb, dbField2, info); if (!info) { snprintf(dbField2, sizeof(dbField2), "%s-asn.snow", dbField); snprintf(expression2, sizeof(expression2), "%s.asn", expression); snprintf(friendlyName2, sizeof(friendlyName2), "%s ASN", friendlyName); snprintf(rawField, sizeof(rawField), "%s-asn.raw", dbField); snprintf(help2, sizeof(help2), "GeoIP ASN string calculated from the %s", help); moloch_session_add_field_proxy(group, "textfield", expression2, friendlyName2, dbField2, help2, "rawField", rawField, NULL); } snprintf(dbField2, sizeof(dbField2), "%s-rir", dbField); HASH_FIND(d_, fieldsByDb, dbField2, info); if (!info) { snprintf(expression2, sizeof(expression2), "%s.rir", expression); snprintf(friendlyName2, sizeof(friendlyName2), "%s RIR", friendlyName); snprintf(help2, sizeof(help2), "Regional Internet Registry string calculated from %s", help); moloch_db_add_field(group, "uptermfield", expression2, friendlyName2, dbField2, help2, FALSE, empty_va_list); } } return minfo->pos; }
int bridge__connect(struct mosquitto_db *db, struct mosquitto *context) { int rc, rc2; int i; char *notification_topic; int notification_topic_len; uint8_t notification_payload; if(!context || !context->bridge) return MOSQ_ERR_INVAL; context->state = mosq_cs_new; context->sock = INVALID_SOCKET; context->last_msg_in = mosquitto_time(); context->next_msg_out = mosquitto_time() + context->bridge->keepalive; context->keepalive = context->bridge->keepalive; context->clean_session = context->bridge->clean_session; context->in_packet.payload = NULL; context->ping_t = 0; context->bridge->lazy_reconnect = false; bridge__packet_cleanup(context); db__message_reconnect_reset(db, context); if(context->clean_session){ db__messages_delete(db, context); } /* Delete all local subscriptions even for clean_session==false. We don't * remove any messages and the next loop carries out the resubscription * anyway. This means any unwanted subs will be removed. */ sub__clean_session(db, context); for(i=0; i<context->bridge->topic_count; i++){ if(context->bridge->topics[i].direction == bd_out || context->bridge->topics[i].direction == bd_both){ log__printf(NULL, MOSQ_LOG_DEBUG, "Bridge %s doing local SUBSCRIBE on topic %s", context->id, context->bridge->topics[i].local_topic); if(sub__add(db, context, context->bridge->topics[i].local_topic, context->bridge->topics[i].qos, &db->subs)) return 1; } } if(context->bridge->notifications){ if(context->bridge->notification_topic){ if(!context->bridge->initial_notification_done){ notification_payload = '0'; db__messages_easy_queue(db, context, context->bridge->notification_topic, 1, 1, ¬ification_payload, 1); context->bridge->initial_notification_done = true; } if (!context->bridge->notifications_local_only) { notification_payload = '0'; rc = will__set(context, context->bridge->notification_topic, 1, ¬ification_payload, 1, true); if(rc != MOSQ_ERR_SUCCESS){ return rc; } } }else{ notification_topic_len = strlen(context->bridge->remote_clientid)+strlen("$SYS/broker/connection//state"); notification_topic = mosquitto__malloc(sizeof(char)*(notification_topic_len+1)); if(!notification_topic) return MOSQ_ERR_NOMEM; snprintf(notification_topic, notification_topic_len+1, "$SYS/broker/connection/%s/state", context->bridge->remote_clientid); if(!context->bridge->initial_notification_done){ notification_payload = '0'; db__messages_easy_queue(db, context, notification_topic, 1, 1, ¬ification_payload, 1); context->bridge->initial_notification_done = true; } if (!context->bridge->notifications_local_only) { notification_payload = '0'; rc = will__set(context, notification_topic, 1, ¬ification_payload, 1, true); mosquitto__free(notification_topic); if(rc != MOSQ_ERR_SUCCESS){ return rc; } } } } log__printf(NULL, MOSQ_LOG_NOTICE, "Connecting bridge %s (%s:%d)", context->bridge->name, context->bridge->addresses[context->bridge->cur_address].address, context->bridge->addresses[context->bridge->cur_address].port); rc = net__socket_connect(context, context->bridge->addresses[context->bridge->cur_address].address, context->bridge->addresses[context->bridge->cur_address].port, NULL, false); if(rc > 0){ if(rc == MOSQ_ERR_TLS){ net__socket_close(db, context); return rc; /* Error already printed */ }else if(rc == MOSQ_ERR_ERRNO){ log__printf(NULL, MOSQ_LOG_ERR, "Error creating bridge: %s.", strerror(errno)); }else if(rc == MOSQ_ERR_EAI){ log__printf(NULL, MOSQ_LOG_ERR, "Error creating bridge: %s.", gai_strerror(errno)); } return rc; }else if(rc == MOSQ_ERR_CONN_PENDING){ context->state = mosq_cs_connect_pending; } HASH_ADD(hh_sock, db->contexts_by_sock, sock, sizeof(context->sock), context); rc2 = send__connect(context, context->keepalive, context->clean_session); if(rc2 == MOSQ_ERR_SUCCESS){ return rc; }else if(rc2 == MOSQ_ERR_ERRNO && errno == ENOTCONN){ return MOSQ_ERR_SUCCESS; }else{ if(rc2 == MOSQ_ERR_TLS){ return rc2; /* Error already printed */ }else if(rc2 == MOSQ_ERR_ERRNO){ log__printf(NULL, MOSQ_LOG_ERR, "Error creating bridge: %s.", strerror(errno)); }else if(rc2 == MOSQ_ERR_EAI){ log__printf(NULL, MOSQ_LOG_ERR, "Error creating bridge: %s.", gai_strerror(errno)); } net__socket_close(db, context); return rc2; } }
void handle_probe_req(struct hostapd_data *hapd, const struct ieee80211_mgmt *mgmt, size_t len, int ssi_signal) { u8 *resp; struct ieee802_11_elems elems; const u8 *ie; size_t ie_len; struct sta_info *sta = NULL; size_t i, resp_len; int noack; enum ssid_match_result res; int iterate = 0; ie = mgmt->u.probe_req.variable; if (len < IEEE80211_HDRLEN + sizeof(mgmt->u.probe_req)) return; ie_len = len - (IEEE80211_HDRLEN + sizeof(mgmt->u.probe_req)); for (i = 0; hapd->probereq_cb && i < hapd->num_probereq_cb; i++) if (hapd->probereq_cb[i].cb(hapd->probereq_cb[i].ctx, mgmt->sa, mgmt->da, mgmt->bssid, ie, ie_len, ssi_signal) > 0) return; if (!hapd->iconf->send_probe_response) return; if (ieee802_11_parse_elems(ie, ie_len, &elems, 0) == ParseFailed) { wpa_printf(MSG_DEBUG, "Could not parse ProbeReq from " MACSTR, MAC2STR(mgmt->sa)); return; } if ((!elems.ssid || !elems.supp_rates)) { wpa_printf(MSG_DEBUG, "STA " MACSTR " sent probe request " "without SSID or supported rates element", MAC2STR(mgmt->sa)); return; } #ifdef CONFIG_P2P if (hapd->p2p && elems.wps_ie) { struct wpabuf *wps; wps = ieee802_11_vendor_ie_concat(ie, ie_len, WPS_DEV_OUI_WFA); if (wps && !p2p_group_match_dev_type(hapd->p2p_group, wps)) { wpa_printf(MSG_MSGDUMP, "P2P: Ignore Probe Request " "due to mismatch with Requested Device " "Type"); wpabuf_free(wps); return; } wpabuf_free(wps); } if (hapd->p2p && elems.p2p) { struct wpabuf *p2p; p2p = ieee802_11_vendor_ie_concat(ie, ie_len, P2P_IE_VENDOR_TYPE); if (p2p && !p2p_group_match_dev_id(hapd->p2p_group, p2p)) { wpa_printf(MSG_MSGDUMP, "P2P: Ignore Probe Request " "due to mismatch with Device ID"); wpabuf_free(p2p); return; } wpabuf_free(p2p); } #endif /* CONFIG_P2P */ if (hapd->conf->ignore_broadcast_ssid && elems.ssid_len == 0 && elems.ssid_list_len == 0 && !hapd->iconf->enable_mana) { wpa_printf(MSG_MSGDUMP, "Probe Request from " MACSTR " for " "broadcast SSID ignored", MAC2STR(mgmt->sa)); return; } sta = ap_get_sta(hapd, mgmt->sa); #ifdef CONFIG_P2P if ((hapd->conf->p2p & P2P_GROUP_OWNER) && elems.ssid_len == P2P_WILDCARD_SSID_LEN && os_memcmp(elems.ssid, P2P_WILDCARD_SSID, P2P_WILDCARD_SSID_LEN) == 0) { /* Process P2P Wildcard SSID like Wildcard SSID */ elems.ssid_len = 0; } #endif /* CONFIG_P2P */ res = ssid_match(hapd, elems.ssid, elems.ssid_len, elems.ssid_list, elems.ssid_list_len); // todo handle ssid_list see ssid_match for code // todo change emit code below (global flag?) if (res == EXACT_SSID_MATCH) { //Probed for configured address if (hapd->iconf->enable_mana) { wpa_printf(MSG_INFO,"MANA - Directed probe request for actual/legitimate SSID '%s' from " MACSTR "",wpa_ssid_txt(elems.ssid, elems.ssid_len),MAC2STR(mgmt->sa)); } if (sta) { sta->ssid_probe = &hapd->conf->ssid; sta->ssid_probe_mana = &hapd->conf->ssid; } } else if (res == NO_SSID_MATCH) { //Probed for unseen SSID wpa_printf(MSG_INFO,"MANA - Directed probe request for foreign SSID '%s' from " MACSTR "",wpa_ssid_txt(elems.ssid, elems.ssid_len),MAC2STR(mgmt->sa)); if (hapd->iconf->enable_mana) { if (sta) { // Make hostapd think they probed for us, necessary for security policy sta->ssid_probe = &hapd->conf->ssid; // Store what was actually probed for sta->ssid_probe_mana = (struct hostapd_ssid*)os_malloc(sizeof(struct hostapd_ssid)); os_memcpy(sta->ssid_probe_mana,&hapd->conf->ssid,sizeof(hapd->conf->ssid)); os_memcpy(sta->ssid_probe_mana->ssid, elems.ssid, elems.ssid_len); sta->ssid_probe_mana->ssid[elems.ssid_len] = '\0'; sta->ssid_probe_mana->ssid_len = elems.ssid_len; } if (hapd->iconf->mana_loud) { // Check if the SSID probed for is in the hash for this STA struct mana_ssid *d = NULL; HASH_FIND_STR(mana_ssidhash, wpa_ssid_txt(elems.ssid, elems.ssid_len), d); if (d == NULL) { wpa_printf(MSG_DEBUG, "MANA - Adding SSID %s(%d) for STA " MACSTR " to the hash.", wpa_ssid_txt(elems.ssid, elems.ssid_len), elems.ssid_len, MAC2STR(mgmt->sa)); d = (struct mana_ssid*)os_malloc(sizeof(struct mana_ssid)); os_memcpy(d->ssid_txt, wpa_ssid_txt(elems.ssid, elems.ssid_len), elems.ssid_len+1); os_memcpy(d->ssid, elems.ssid, elems.ssid_len); d->ssid_len = elems.ssid_len; //os_memcpy(d->sta_addr, mgmt->sa, ETH_ALEN); HASH_ADD_STR(mana_ssidhash, ssid_txt, d); log_ssid(elems.ssid, elems.ssid_len, mgmt->sa); } } else { //Not loud mode, Check if the STA probing is in our hash struct mana_mac *newsta = NULL; //char strmac[18]; //snprintf(strmac, sizeof(strmac), MACSTR, MAC2STR(mgmt->sa)); HASH_FIND(hh,mana_machash, mgmt->sa, 6, newsta); if (newsta == NULL) { //MAC not seen before adding to hash wpa_printf(MSG_DEBUG, "MANA - Adding SSID %s(%d) for STA " MACSTR " to the hash.", wpa_ssid_txt(elems.ssid, elems.ssid_len), elems.ssid_len, MAC2STR(mgmt->sa)); //Add STA newsta = (struct mana_mac*)os_malloc(sizeof(struct mana_mac)); os_memcpy(newsta->sta_addr, mgmt->sa, ETH_ALEN); //os_memcpy(newsta->mac_txt, strmac, sizeof(strmac)); newsta->ssids = NULL; HASH_ADD(hh,mana_machash, sta_addr, 6, newsta); //Add SSID to subhash struct mana_ssid *newssid = os_malloc(sizeof(struct mana_ssid)); os_memcpy(newssid->ssid_txt, wpa_ssid_txt(elems.ssid, elems.ssid_len), elems.ssid_len+1); os_memcpy(newssid->ssid, elems.ssid, elems.ssid_len); newssid->ssid_len = elems.ssid_len; HASH_ADD_STR(newsta->ssids, ssid_txt, newssid); log_ssid(elems.ssid, elems.ssid_len, mgmt->sa); } else { //Seen MAC, check if SSID is new // Check if the SSID probed for is in the hash for this STA struct mana_ssid *newssid = NULL; HASH_FIND_STR(newsta->ssids, wpa_ssid_txt(elems.ssid, elems.ssid_len), newssid); if (newssid == NULL) { //SSID not found, add to sub hash newssid = (struct mana_ssid*)os_malloc(sizeof(struct mana_ssid)); os_memcpy(newssid->ssid_txt, wpa_ssid_txt(elems.ssid, elems.ssid_len), elems.ssid_len+1); os_memcpy(newssid->ssid, elems.ssid, elems.ssid_len); newssid->ssid_len = elems.ssid_len; HASH_ADD_STR(newsta->ssids, ssid_txt, newssid); log_ssid(elems.ssid, elems.ssid_len, mgmt->sa); } } } } else { //No SSID Match and no Mana behave as normal if (!(mgmt->da[0] & 0x01)) { wpa_printf(MSG_DEBUG, "Probe Request from " MACSTR " for foreign SSID '%s' (DA " MACSTR ")%s", MAC2STR(mgmt->sa), wpa_ssid_txt(elems.ssid, elems.ssid_len), MAC2STR(mgmt->da), elems.ssid_list ? " (SSID list)" : ""); } return; } } else { //Probed for wildcard i.e. WILDCARD_SSID_MATCH if (hapd->iconf->enable_mana) { wpa_printf(MSG_DEBUG,"MANA - Broadcast probe request from " MACSTR "",MAC2STR(mgmt->sa)); iterate = 1; //iterate through hash emitting multiple probe responses } if (sta) sta->ssid_probe = &hapd->conf->ssid; } #ifdef CONFIG_INTERWORKING if (hapd->conf->interworking && elems.interworking && elems.interworking_len >= 1) { u8 ant = elems.interworking[0] & 0x0f; if (ant != INTERWORKING_ANT_WILDCARD && ant != hapd->conf->access_network_type) { wpa_printf(MSG_MSGDUMP, "Probe Request from " MACSTR " for mismatching ANT %u ignored", MAC2STR(mgmt->sa), ant); return; } } if (hapd->conf->interworking && elems.interworking && (elems.interworking_len == 7 || elems.interworking_len == 9)) { const u8 *hessid; if (elems.interworking_len == 7) hessid = elems.interworking + 1; else hessid = elems.interworking + 1 + 2; if (!is_broadcast_ether_addr(hessid) && os_memcmp(hessid, hapd->conf->hessid, ETH_ALEN) != 0) { wpa_printf(MSG_MSGDUMP, "Probe Request from " MACSTR " for mismatching HESSID " MACSTR " ignored", MAC2STR(mgmt->sa), MAC2STR(hessid)); return; } } #endif /* CONFIG_INTERWORKING */ #ifdef CONFIG_P2P if ((hapd->conf->p2p & P2P_GROUP_OWNER) && supp_rates_11b_only(&elems)) { /* Indicates support for 11b rates only */ wpa_printf(MSG_EXCESSIVE, "P2P: Ignore Probe Request from " MACSTR " with only 802.11b rates", MAC2STR(mgmt->sa)); return; } #endif /* CONFIG_P2P */ /* TODO: verify that supp_rates contains at least one matching rate * with AP configuration */ #ifdef CONFIG_TESTING_OPTIONS if (hapd->iconf->ignore_probe_probability > 0.0 && drand48() < hapd->iconf->ignore_probe_probability) { wpa_printf(MSG_INFO, "TESTING: ignoring probe request from " MACSTR, MAC2STR(mgmt->sa)); return; } #endif /* CONFIG_TESTING_OPTIONS */ resp = hostapd_gen_probe_resp(hapd, sta, elems.ssid, elems.ssid_len, mgmt, elems.p2p != NULL, &resp_len); if (resp == NULL) return; /* * If this is a broadcast probe request, apply no ack policy to avoid * excessive retries. */ noack = !!(res == WILDCARD_SSID_MATCH && is_broadcast_ether_addr(mgmt->da)); if (hostapd_drv_send_mlme(hapd, resp, resp_len, noack) < 0) wpa_printf(MSG_INFO, "handle_probe_req: send failed"); os_free(resp); if (iterate) { // Only iterate through the hash if this is set struct ieee80211_mgmt *resp2; size_t resp2_len; struct mana_ssid *k; if (hapd->iconf->mana_loud) { for ( k = mana_ssidhash; k != NULL; k = (struct mana_ssid*)(k->hh.next)) { wpa_printf(MSG_DEBUG, "MANA - Attempting to generate LOUD Broadcast response : %s (%zu) for STA " MACSTR, k->ssid_txt, k->ssid_len, MAC2STR(mgmt->sa)); resp2 = (struct ieee80211_mgmt*)hostapd_gen_probe_resp(hapd, sta, k->ssid, k->ssid_len, mgmt, elems.p2p != NULL, &resp2_len); if (resp2 == NULL) { wpa_printf(MSG_ERROR, "MANA - Could not generate SSID response for %s (%zu)", k->ssid_txt, k->ssid_len); } else { wpa_printf(MSG_DEBUG, "MANA - Successfully generated SSID response for %s (len %zu) to station : " MACSTR, k->ssid_txt, k->ssid_len, MAC2STR(resp2->da)); if (hostapd_drv_send_mlme(hapd, resp2, resp2_len, noack) < 0) { wpa_printf(MSG_ERROR, "MANA - Failed sending prove response for SSID %s (%zu)", k->ssid_txt, k->ssid_len); } os_free(resp2); } } } else { //Not loud mode, only send for one mac struct mana_mac *newsta = NULL; char strmac[18]; snprintf(strmac, sizeof(strmac), MACSTR, MAC2STR(mgmt->sa)); HASH_FIND(hh, mana_machash, mgmt->sa, 6, newsta); if (newsta != NULL) { for ( k = newsta->ssids; k != NULL; k = (struct mana_ssid*)(k->hh.next)) { wpa_printf(MSG_INFO, "MANA - Attempting to generated Broadcast response : %s (%zu) for STA %s", k->ssid_txt, k->ssid_len, strmac); resp2 = (struct ieee80211_mgmt*)hostapd_gen_probe_resp(hapd, sta, k->ssid, k->ssid_len, mgmt, elems.p2p != NULL, &resp2_len); if (resp2 == NULL) { wpa_printf(MSG_ERROR, "MANA - Could not generate SSID response for %s (%zu)", k->ssid_txt, k->ssid_len); } else { wpa_printf(MSG_DEBUG, "MANA - Successfully generated SSID response for %s (len %zu) to station : " MACSTR, k->ssid_txt, k->ssid_len, MAC2STR(resp2->da)); if (hostapd_drv_send_mlme(hapd, resp2, resp2_len, noack) < 0) { wpa_printf(MSG_ERROR, "MANA - Failed sending prove response for SSID %s (%zu)", k->ssid_txt, k->ssid_len); } os_free(resp2); } } } } } wpa_printf(MSG_EXCESSIVE, "STA " MACSTR " sent probe request for %s " "SSID", MAC2STR(mgmt->sa), elems.ssid_len == 0 ? "broadcast" : "our"); }
static gboolean moloch_http_curl_watch_open_callback(int fd, GIOCondition condition, gpointer serverV) { MolochHttpServer_t *server = serverV; struct sockaddr_storage localAddressStorage, remoteAddressStorage; socklen_t addressLength = sizeof(localAddressStorage); int rc = getsockname(fd, (struct sockaddr*)&localAddressStorage, &addressLength); if (rc != 0) return FALSE; addressLength = sizeof(remoteAddressStorage); rc = getpeername(fd, (struct sockaddr*)&remoteAddressStorage, &addressLength); if (rc != 0) return FALSE; char sessionId[MOLOCH_SESSIONID_LEN]; int localPort, remotePort; char remoteIp[INET6_ADDRSTRLEN+2]; if (localAddressStorage.ss_family == AF_INET) { struct sockaddr_in *localAddress = (struct sockaddr_in *)&localAddressStorage; struct sockaddr_in *remoteAddress = (struct sockaddr_in *)&remoteAddressStorage; moloch_session_id(sessionId, localAddress->sin_addr.s_addr, localAddress->sin_port, remoteAddress->sin_addr.s_addr, remoteAddress->sin_port); localPort = ntohs(localAddress->sin_port); remotePort = ntohs(remoteAddress->sin_port); inet_ntop(AF_INET, &remoteAddress->sin_addr, remoteIp, sizeof(remoteIp)); } else { struct sockaddr_in6 *localAddress = (struct sockaddr_in6 *)&localAddressStorage; struct sockaddr_in6 *remoteAddress = (struct sockaddr_in6 *)&remoteAddressStorage; moloch_session_id6(sessionId, localAddress->sin6_addr.s6_addr, localAddress->sin6_port, remoteAddress->sin6_addr.s6_addr, remoteAddress->sin6_port); localPort = ntohs(localAddress->sin6_port); remotePort = ntohs(remoteAddress->sin6_port); inet_ntop(AF_INET6, &remoteAddress->sin6_addr, remoteIp+1, sizeof(remoteIp)-2); remoteIp[0] = '['; strcat(remoteIp, "]"); } LOG("Connected %d/%d - %s %d->%s:%d - fd:%d", server->outstanding, server->connections, server->names[0], localPort, remoteIp, remotePort, fd); MolochHttpConn_t *conn; MOLOCH_LOCK(connections); BIT_SET(fd, connectionsSet); HASH_FIND(h_, connections, sessionId, conn); if (!conn) { conn = MOLOCH_TYPE_ALLOC0(MolochHttpConn_t); HASH_ADD(h_, connections, sessionId, conn); memcpy(&conn->sessionId, sessionId, sessionId[0]); server->connections++; } else { char buf[1000]; LOG("ERROR - Already added %x %s", condition, moloch_session_id_string(sessionId, buf)); } MOLOCH_UNLOCK(connections); moloch_http_curlm_check_multi_info(server); return FALSE; }
static ssize_t fi_ibv_rdm_process_connect_request(struct rdma_cm_event *event, struct fi_ibv_rdm_ep *ep) { struct ibv_qp_init_attr qp_attr; struct rdma_conn_param cm_params; struct fi_ibv_rdm_tagged_conn *conn = NULL; struct rdma_cm_id *id = event->id; ssize_t ret = FI_SUCCESS; char *p = (char *) event->param.conn.private_data; if (ep->is_closing) { int rej_message = 0xdeadbeef; if (rdma_reject(id, &rej_message, sizeof(int))) { VERBS_INFO_ERRNO(FI_LOG_AV, "rdma_reject\n", errno); ret = -errno; if (rdma_destroy_id(id)) { VERBS_INFO_ERRNO(FI_LOG_AV, "rdma_destroy_id\n", errno); ret = (ret == FI_SUCCESS) ? -errno : ret; } } assert(ret == FI_SUCCESS); return ret; } HASH_FIND(hh, fi_ibv_rdm_tagged_conn_hash, p, FI_IBV_RDM_DFLT_ADDRLEN, conn); if (!conn) { conn = memalign(FI_IBV_RDM_MEM_ALIGNMENT, sizeof(*conn)); if (!conn) return -FI_ENOMEM; memset(conn, 0, sizeof(struct fi_ibv_rdm_tagged_conn)); conn->state = FI_VERBS_CONN_ALLOCATED; dlist_init(&conn->postponed_requests_head); fi_ibv_rdm_unpack_cm_params(&event->param.conn, conn, ep); fi_ibv_rdm_conn_init_cm_role(conn, ep); FI_INFO(&fi_ibv_prov, FI_LOG_AV, "CONN REQUEST, NOT found in hash, new conn %p %d, addr %s:%u, HASH ADD\n", conn, conn->cm_role, inet_ntoa(conn->addr.sin_addr), ntohs(conn->addr.sin_port)); HASH_ADD(hh, fi_ibv_rdm_tagged_conn_hash, addr, FI_IBV_RDM_DFLT_ADDRLEN, conn); } else { if (conn->cm_role != FI_VERBS_CM_ACTIVE) { /* * Do it before rdma_create_qp since that call would * modify event->param.conn.private_data buffer */ fi_ibv_rdm_unpack_cm_params(&event->param.conn, conn, ep); } FI_INFO(&fi_ibv_prov, FI_LOG_AV, "CONN REQUEST, FOUND in hash, conn %p %d, addr %s:%u\n", conn, conn->cm_role, inet_ntoa(conn->addr.sin_addr), ntohs(conn->addr.sin_port)); } if (conn->cm_role == FI_VERBS_CM_ACTIVE) { int rej_message = 0xdeadbeef; if (rdma_reject(id, &rej_message, sizeof(rej_message))) { VERBS_INFO_ERRNO(FI_LOG_AV, "rdma_reject\n", errno); ret = -errno; if (rdma_destroy_id(id)) { VERBS_INFO_ERRNO(FI_LOG_AV, "rdma_destroy_id\n", errno); ret = (ret == FI_SUCCESS) ? -errno : ret; } } if (conn->state == FI_VERBS_CONN_ALLOCATED) { ret = fi_ibv_rdm_start_connection(ep, conn); if (ret != FI_SUCCESS) goto err; } } else { assert(conn->state == FI_VERBS_CONN_ALLOCATED || conn->state == FI_VERBS_CONN_STARTED); const size_t idx = (conn->cm_role == FI_VERBS_CM_PASSIVE) ? 0 : 1; conn->state = FI_VERBS_CONN_STARTED; assert (conn->id[idx] == NULL); conn->id[idx] = id; ret = fi_ibv_rdm_prepare_conn_memory(ep, conn); if (ret != FI_SUCCESS) goto err; fi_ibv_rdm_tagged_init_qp_attributes(&qp_attr, ep); if (rdma_create_qp(id, ep->domain->pd, &qp_attr)) { ret = -errno; goto err; } conn->qp[idx] = id->qp; ret = fi_ibv_rdm_repost_receives(conn, ep, ep->rq_wr_depth); if (ret < 0) { VERBS_INFO(FI_LOG_AV, "repost receives failed\n"); goto err; } else { ret = FI_SUCCESS; } id->context = conn; fi_ibv_rdm_pack_cm_params(&cm_params, conn, ep); if (rdma_accept(id, &cm_params)) { VERBS_INFO_ERRNO(FI_LOG_AV, "rdma_accept\n", errno); ret = -errno; goto err; } if (cm_params.private_data) { free((void *) cm_params.private_data); } } return ret; err: /* ret err code is already set here, just cleanup resources */ fi_ibv_rdm_conn_cleanup(conn); return ret; }
void hnd_post_rd(coap_context_t *ctx, struct coap_resource_t *resource, coap_address_t *peer, coap_pdu_t *request, str *token, coap_pdu_t *response, void *userdata) { coap_resource_t *r; coap_opt_iterator_t opt_iter; coap_opt_t *query; #define LOCSIZE 68 unsigned char *loc; size_t loc_size; str h = {0, NULL}, ins = {0, NULL}, rt = {0, NULL}, lt = {0, NULL}; /* store query parameters */ unsigned char *buf; loc = (unsigned char *)coap_malloc(LOCSIZE); if (!loc) { response->hdr->code = COAP_RESPONSE_CODE(500); return; } memcpy(loc, RD_ROOT_STR, RD_ROOT_SIZE); loc_size = RD_ROOT_SIZE; loc[loc_size++] = '/'; /* store query parameters for later use */ query = coap_check_option(request, COAP_OPTION_URI_QUERY, &opt_iter); if (query) { parse_param((unsigned char *)"h", 1, COAP_OPT_VALUE(query), COAP_OPT_LENGTH(query), &h); parse_param((unsigned char *)"ins", 3, COAP_OPT_VALUE(query), COAP_OPT_LENGTH(query), &ins); parse_param((unsigned char *)"lt", 2, COAP_OPT_VALUE(query), COAP_OPT_LENGTH(query), <); parse_param((unsigned char *)"rt", 2, COAP_OPT_VALUE(query), COAP_OPT_LENGTH(query), &rt); } if (h.length) { /* client has specified a node name */ memcpy(loc + loc_size, h.s, min(h.length, LOCSIZE - loc_size - 1)); loc_size += min(h.length, LOCSIZE - loc_size - 1); if (ins.length && loc_size > 1) { loc[loc_size++] = '-'; memcpy((char *)(loc + loc_size), ins.s, min(ins.length, LOCSIZE - loc_size - 1)); loc_size += min(ins.length, LOCSIZE - loc_size - 1); } } else { /* generate node identifier */ loc_size += snprintf((char *)(loc + loc_size), LOCSIZE - loc_size - 1, "%x", request->hdr->id); if (loc_size > 1) { if (ins.length) { loc[loc_size++] = '-'; memcpy((char *)(loc + loc_size), ins.s, min(ins.length, LOCSIZE - loc_size - 1)); loc_size += min(ins.length, LOCSIZE - loc_size - 1); } else { coap_tick_t now; coap_ticks(&now); loc_size += snprintf((char *)(loc + loc_size), LOCSIZE - loc_size - 1, "-%x", now); } } } /* TODO: * - use lt to check expiration */ r = coap_resource_init(loc, loc_size, COAP_RESOURCE_FLAGS_RELEASE_URI); coap_register_handler(r, COAP_REQUEST_GET, hnd_get_resource); coap_register_handler(r, COAP_REQUEST_PUT, hnd_put_resource); coap_register_handler(r, COAP_REQUEST_DELETE, hnd_delete_resource); if (ins.s) { buf = (unsigned char *)coap_malloc(ins.length + 2); if (buf) { /* add missing quotes */ buf[0] = '"'; memcpy(buf + 1, ins.s, ins.length); buf[ins.length + 1] = '"'; coap_add_attr(r, (unsigned char *)"ins", 3, buf, ins.length + 2, COAP_ATTR_FLAGS_RELEASE_VALUE); } } if (rt.s) { buf = (unsigned char *)coap_malloc(rt.length + 2); if (buf) { /* add missing quotes */ buf[0] = '"'; memcpy(buf + 1, rt.s, rt.length); buf[rt.length + 1] = '"'; coap_add_attr(r, (unsigned char *)"rt", 2, buf, rt.length + 2, COAP_ATTR_FLAGS_RELEASE_VALUE); } } add_source_address(r, peer); { rd_t *rd; rd = make_rd(peer, request); if (rd) { coap_hash_path(loc, loc_size, rd->key); HASH_ADD(hh, resources, key, sizeof(coap_key_t), rd); } else { /* FIXME: send error response and delete r */ } } coap_add_resource(ctx, r); /* create response */ response->hdr->code = COAP_RESPONSE_CODE(201); { /* split path into segments and add Location-Path options */ unsigned char _b[LOCSIZE]; unsigned char *b = _b; size_t buflen = sizeof(_b); int nseg; nseg = coap_split_path(loc, loc_size, b, &buflen); while (nseg--) { coap_add_option(response, COAP_OPTION_LOCATION_PATH, COAP_OPT_LENGTH(b), COAP_OPT_VALUE(b)); b += COAP_OPT_SIZE(b); } } }