diff --git a/dap-sdk/CMakeLists.txt b/dap-sdk/CMakeLists.txt
index cc44d581e1355d8536edad52b489ecc24a46f550..d1053b93e441561481c424d17dddc74337d86cd5 100644
--- a/dap-sdk/CMakeLists.txt
+++ b/dap-sdk/CMakeLists.txt
@@ -1,4 +1,4 @@
-set(DAP_SDK_NATIVE_VERSION "2.0-11")
+set(DAP_SDK_NATIVE_VERSION "2.0-12")
 # Core 
 if (DAPSDK_MODULES MATCHES "core")
     # Core
@@ -22,5 +22,5 @@ endif()
 # Networking server
 if (DAPSDK_MODULES MATCHES "network-server")
     add_subdirectory(net/server)
-    add_subdirectory(net/server-udp)
+#    add_subdirectory(net/server-udp)
 endif()
diff --git a/dap-sdk/net/core/dap_server.c b/dap-sdk/net/core/dap_server.c
index 6f49c8298997a1de133f432a7c9449a25fd95500..6a3dd124379a9eee9c6eeef7d1e13172164ced61 100644
--- a/dap-sdk/net/core/dap_server.c
+++ b/dap-sdk/net/core/dap_server.c
@@ -64,7 +64,6 @@ static dap_events_socket_t * s_es_server_create(dap_events_t * a_events, int a_s
 static void s_es_server_accept(dap_events_socket_t *a_es, int a_remote_socket, struct sockaddr* a_remote_addr);
 static void s_es_server_error(dap_events_socket_t *a_es, int a_arg);
 static void s_es_server_new(dap_events_socket_t *a_es, void * a_arg);
-static void s_server_delete(dap_server_t * a_server);
 /**
  * @brief dap_server_init
  * @return
@@ -86,14 +85,17 @@ void dap_server_deinit()
  * @brief dap_server_delete
  * @param a_server
  */
-void s_server_delete(dap_server_t * a_server)
+void dap_server_delete(dap_server_t *a_server)
 {
-    if(a_server->delete_callback)
+   dap_events_socket_remove_and_delete_mt(a_server->es_listener->worker, a_server->es_listener);
+   if(a_server->delete_callback)
         a_server->delete_callback(a_server,NULL);
    if( a_server->address )
        DAP_DELETE(a_server->address );
    if( a_server->_inheritor )
        DAP_DELETE( a_server->_inheritor );
+   pthread_mutex_destroy(&a_server->started_mutex);
+   pthread_cond_destroy(&a_server->started_cond);
    DAP_DELETE(a_server);
 }
 
@@ -117,6 +119,8 @@ dap_server_t* dap_server_new(dap_events_t *a_events, const char * a_addr, uint16
 
     if(l_server->type == DAP_SERVER_TCP)
         l_server->socket_listener = socket(AF_INET, SOCK_STREAM, 0);
+    else if (l_server->type == DAP_SERVER_UDP)
+        l_server->socket_listener = socket(AF_INET, SOCK_DGRAM, 0);
 
     if (l_server->socket_listener < 0) {
         int l_errno = errno;
@@ -166,6 +170,7 @@ dap_server_t* dap_server_new(dap_events_t *a_events, const char * a_addr, uint16
         dap_worker_t *l_w = dap_events_worker_get(l_worker_id);
         assert(l_w);
         dap_events_socket_t * l_es = dap_events_socket_wrap2( l_server, a_events, l_server->socket_listener, &l_callbacks);
+        l_server->es_listener = l_es;
 
         if ( l_es){
             l_es->type = DESCRIPTOR_TYPE_SOCKET_LISTENING;
diff --git a/dap-sdk/net/core/dap_worker.c b/dap-sdk/net/core/dap_worker.c
index 6a2081799ab911a6521789ccc5478ea2be0922ec..7e2a5c0452b92442280009a060f5d6a373f05a5d 100644
--- a/dap-sdk/net/core/dap_worker.c
+++ b/dap-sdk/net/core/dap_worker.c
@@ -190,8 +190,15 @@ void *dap_worker_thread(void *arg)
                     break;
                     case DESCRIPTOR_TYPE_SOCKET:
                         l_must_read_smth = true;
-                        l_bytes_read = recv(l_cur->fd, (char *) (l_cur->buf_in + l_cur->buf_in_size),
-                                sizeof(l_cur->buf_in) - l_cur->buf_in_size, 0);
+                        if (l_cur->server->type == DAP_SERVER_TCP) {
+                            l_bytes_read = recv(l_cur->fd, (char *) (l_cur->buf_in + l_cur->buf_in_size),
+                                                sizeof(l_cur->buf_in) - l_cur->buf_in_size, 0);
+                        } else if (l_cur->server->type == DAP_SERVER_UDP) {
+                            int l_size = sizeof(l_cur->remote_addr);
+                            l_bytes_read = recvfrom(l_cur->fd, (char *) (l_cur->buf_in + l_cur->buf_in_size),
+                                                    sizeof(l_cur->buf_in) - l_cur->buf_in_size, 0,
+                                                    (struct sockaddr *)&l_cur->remote_addr, &l_size);
+                        }
                         l_errno = errno;
                     break;
                     case DESCRIPTOR_TYPE_SOCKET_LISTENING:
@@ -299,8 +306,14 @@ void *dap_worker_thread(void *arg)
                 int l_errno;
                 switch (l_cur->type){
                     case DESCRIPTOR_TYPE_SOCKET:
-                        l_bytes_sent = send(l_cur->socket, l_cur->buf_out,
-                                l_cur->buf_out_size, MSG_DONTWAIT | MSG_NOSIGNAL);
+                        if (l_cur->server->type == DAP_SERVER_TCP) {
+                            l_bytes_sent = send(l_cur->socket, (const char *)l_cur->buf_out,
+                                                l_cur->buf_out_size, MSG_DONTWAIT | MSG_NOSIGNAL);
+                        } else if (l_cur->server->type == DAP_SERVER_UDP) {
+                            l_bytes_sent = sendto(l_cur->socket, (const char *)l_cur->buf_out,
+                                                  l_cur->buf_out_size, MSG_DONTWAIT | MSG_NOSIGNAL,
+                                                  (struct sockaddr *)&l_cur->remote_addr, sizeof(l_cur->remote_addr));
+                        }
                         l_errno = errno;
                     break;
                     case DESCRIPTOR_TYPE_PIPE:
diff --git a/dap-sdk/net/core/include/dap_events_socket.h b/dap-sdk/net/core/include/dap_events_socket.h
index 68020f1a339071b7269d987bb897aee2b45f6d7f..7e072d9997a451554e85206969315fd315b90900 100644
--- a/dap-sdk/net/core/include/dap_events_socket.h
+++ b/dap-sdk/net/core/include/dap_events_socket.h
@@ -165,7 +165,7 @@ typedef struct dap_events_socket {
     // Stored string representation
     char hostaddr[1024]; // Address
     char service[128];
-    struct sockaddr remote_addr;
+    struct sockaddr_in remote_addr; // For UDP datagrams
 
     // Links to related objects
     dap_events_t *events;
diff --git a/dap-sdk/net/core/include/dap_server.h b/dap-sdk/net/core/include/dap_server.h
index 44bf62135e5756e0d1c05fb1f62937e4d0b1ccc8..6a3ded032f9b2e76aa6048d1b1e4948fbd110a4a 100644
--- a/dap-sdk/net/core/include/dap_server.h
+++ b/dap-sdk/net/core/include/dap_server.h
@@ -51,7 +51,7 @@
 #include "dap_cpu_monitor.h"
 #include "dap_events_socket.h"
 
-typedef enum dap_server_type {DAP_SERVER_TCP} dap_server_type_t;
+typedef enum dap_server_type {DAP_SERVER_TCP, DAP_SERVER_UDP} dap_server_type_t;
 
 
 
@@ -86,3 +86,4 @@ int dap_server_init( ); // Init server module
 void  dap_server_deinit( void ); // Deinit server module
 
 dap_server_t* dap_server_new(dap_events_t *a_events, const char * a_addr, uint16_t a_port, dap_server_type_t a_type);
+void dap_server_delete(dap_server_t *a_server);
diff --git a/modules/net/dap_dns_server.c b/modules/net/dap_dns_server.c
index 8c6907d31e1d1cfe2dfce67005a5db4309669fc7..aecc8ef81f63dac6669ee7ff228150e4b5576933 100644
--- a/modules/net/dap_dns_server.c
+++ b/modules/net/dap_dns_server.c
@@ -191,16 +191,16 @@ dap_dns_zone_callback_t dap_dns_zone_find(char *hostname) {
  * @param arg Unused
  * @return none
  */
-void dap_dns_client_read(dap_events_socket_t *client, void * arg) {
-    UNUSED(arg);
-    if (client->buf_in_size < DNS_HEADER_SIZE) {        // Bad request
+void dap_dns_client_read(dap_events_socket_t *a_es, void *a_arg) {
+    UNUSED(a_arg);
+    if (a_es->buf_in_size < DNS_HEADER_SIZE) {        // Bad request
         return;
     }
     dap_dns_buf_t *dns_message = DAP_NEW(dap_dns_buf_t);
     dap_dns_buf_t *dns_reply = DAP_NEW(dap_dns_buf_t);
-    dns_message->data = DAP_NEW_SIZE(char, client->buf_in_size + 1);
-    dns_message->data[client->buf_in_size] = 0;
-    dap_events_socket_pop_from_buf_in(client, dns_message->data, client->buf_in_size);
+    dns_message->data = DAP_NEW_SIZE(char, a_es->buf_in_size + 1);
+    dns_message->data[a_es->buf_in_size] = 0;
+    dap_events_socket_pop_from_buf_in(a_es, dns_message->data, a_es->buf_in_size);
     dns_message->ptr = 0;
 
     // Parse incoming DNS message
@@ -332,8 +332,8 @@ void dap_dns_client_read(dap_events_socket_t *client, void * arg) {
     dns_reply->data[2] = msg_flags.val >> 8;
     dns_reply->data[3] = msg_flags.val;
     // Send DNS reply
-    dap_events_socket_write_unsafe( client, dns_reply->data, dns_reply->ptr);
-    dap_events_socket_set_writable_unsafe( client, true);
+    dap_events_socket_write_unsafe(a_es, dns_reply->data, dns_reply->ptr);
+    dap_events_socket_set_writable_unsafe(a_es, true);
     dap_string_free(dns_hostname, true);
 cleanup:
     DAP_DELETE(dns_reply->data);
@@ -343,20 +343,15 @@ cleanup:
     return;
 }
 
-void dap_dns_server_start() {
-    s_dns_server = DAP_NEW(dap_dns_server_t);
-    s_dns_server->hash_table = NULL;
-    s_dns_server->instance = dap_udp_server_listen(DNS_LISTEN_PORT);
+void dap_dns_server_start(dap_events_t *a_ev) {
+    s_dns_server = DAP_NEW_Z(dap_dns_server_t);
+    s_dns_server->instance = dap_server_new(a_ev, NULL, DNS_LISTEN_PORT, DAP_SERVER_UDP);
     if (!s_dns_server->instance) {
         log_it(L_ERROR, "Can't start DNS server");
         return;
     }
     s_dns_server->instance->client_callbacks.read_callback = dap_dns_client_read;
-    s_dns_server->instance->client_callbacks.write_callback = NULL;
-    s_dns_server->instance->client_callbacks.new_callback = NULL;
-    s_dns_server->instance->client_callbacks.delete_callback = NULL;
     dap_dns_zone_register(&s_root_alias[0], dap_dns_resolve_hostname);  // root resolver
-    pthread_create(&s_dns_server->udp_thread, NULL, (void *)dap_udp_server_loop, s_dns_server->instance);
 }
 
 void dap_dns_server_stop() {
@@ -369,8 +364,7 @@ void dap_dns_server_stop() {
         DAP_DELETE(current_zone->zone);
         DAP_DELETE(current_zone);
     }
-    // TODO add code to stop udp_thread
-    dap_udp_server_delete(s_dns_server->instance);
+    dap_server_delete(s_dns_server->instance);
     DAP_DELETE(s_dns_server);
 }
 
diff --git a/modules/net/include/dap_dns_server.h b/modules/net/include/dap_dns_server.h
index e36022f8bf2bf4d08d774075ba41a2f1b24540e4..3b462ab5b3638dfea2ec3b43a0728933b4685490 100644
--- a/modules/net/include/dap_dns_server.h
+++ b/modules/net/include/dap_dns_server.h
@@ -116,7 +116,6 @@ typedef struct _dap_dns_zone_hash_t {
 
 typedef struct _dap_dns_server_t {
     dap_server_t *instance;
-    pthread_t udp_thread;
     dap_dns_zone_hash_t *hash_table;
 } dap_dns_server_t;