diff --git a/CMakeLists.txt b/CMakeLists.txt
index 3494e400a6aa23bdbacce296da51b471f410f7d0..1c2dbea53e8bd70178ec81a287f274c9ef70588c 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -2,7 +2,7 @@ project(cellframe-sdk C)
 cmake_minimum_required(VERSION 2.8)
 
 set(CMAKE_C_STANDARD 11)
-set(CELLFRAME_SDK_NATIVE_VERSION "2.8-3")
+set(CELLFRAME_SDK_NATIVE_VERSION "2.8-4")
 add_definitions ("-DCELLFRAME_SDK_VERSION=\"${CELLFRAME_SDK_NATIVE_VERSION}\"")
 set(DAPSDK_MODULES "")
 
diff --git a/dap-sdk/crypto/include/dap_enc_dilithium.h b/dap-sdk/crypto/include/dap_enc_dilithium.h
index 7f285580f12b1e512c1275f5a9dd1549deb5d57c..e9352f3c9f026c0ed0b78626ffd886c3b297c23c 100755
--- a/dap-sdk/crypto/include/dap_enc_dilithium.h
+++ b/dap-sdk/crypto/include/dap_enc_dilithium.h
@@ -37,6 +37,9 @@ dilithium_signature_t* dap_enc_dilithium_read_signature(uint8_t *a_buf, size_t a
 uint8_t* dap_enc_dilithium_write_private_key(const dilithium_private_key_t* a_private_key, size_t *a_buflen_out);
 uint8_t* dap_enc_dilithium_write_public_key(const dilithium_public_key_t* a_public_key, size_t *a_buflen_out);
 dilithium_private_key_t* dap_enc_dilithium_read_private_key(const uint8_t *a_buf, size_t a_buflen);
+dilithium_private_key_t* dap_enc_dilithium_read_private_key_old(const uint8_t *a_buf, size_t a_buflen);
+
 dilithium_public_key_t* dap_enc_dilithium_read_public_key(const uint8_t *a_buf, size_t a_buflen);
+dilithium_public_key_t* dap_enc_dilithium_read_public_key_old(const uint8_t *a_buf, size_t a_buflen);
 
 #endif
diff --git a/dap-sdk/crypto/include/dap_enc_key.h b/dap-sdk/crypto/include/dap_enc_key.h
index 42711803e73cfa8bc21d79d8a920723224cbeb79..9bbfeab50db331fd1edda9ce7119ad9505da9bea 100755
--- a/dap-sdk/crypto/include/dap_enc_key.h
+++ b/dap-sdk/crypto/include/dap_enc_key.h
@@ -255,6 +255,7 @@ uint8_t* dap_enc_key_serealize_priv_key(dap_enc_key_t *a_key, size_t *a_buflen_o
 uint8_t* dap_enc_key_serealize_pub_key(dap_enc_key_t *a_key, size_t *a_buflen_out);
 int dap_enc_key_deserealize_priv_key(dap_enc_key_t *a_key, const uint8_t *a_buf, size_t a_buflen);
 int dap_enc_key_deserealize_pub_key(dap_enc_key_t *a_key, const uint8_t *a_buf, size_t a_buflen);
+int dap_enc_key_deserealize_pub_key_old(dap_enc_key_t *a_key, const uint8_t *a_buf, size_t a_buflen);
 
 dap_enc_key_serealize_t* dap_enc_key_serealize(dap_enc_key_t * key);
 dap_enc_key_t* dap_enc_key_deserealize(const void *buf, size_t buf_size);
diff --git a/dap-sdk/crypto/src/dap_enc.c b/dap-sdk/crypto/src/dap_enc.c
index 28f0f753f051cea01042033d824497201265f22a..bb388202b73abac4f794c96408768490c7ad4102 100755
--- a/dap-sdk/crypto/src/dap_enc.c
+++ b/dap-sdk/crypto/src/dap_enc.c
@@ -41,6 +41,7 @@
 int dap_enc_init()
 {
     srand(time(NULL));
+    dap_enc_key_init();
     return 0;
 }
 
diff --git a/dap-sdk/crypto/src/dap_enc_dilithium.c b/dap-sdk/crypto/src/dap_enc_dilithium.c
index b8509aabdff1a00d12990ebdadc0c2ce8e426c08..076b2b8cac4a6d83c0bbc8be6bb2029ab65d44ea 100755
--- a/dap-sdk/crypto/src/dap_enc_dilithium.c
+++ b/dap-sdk/crypto/src/dap_enc_dilithium.c
@@ -10,6 +10,10 @@
 
 static enum DAP_DILITHIUM_SIGN_SECURITY _dilithium_type = DILITHIUM_MIN_SIZE; // by default
 
+//// WARNING! Its because of accident with wrong sizes on mobile 32bit platforms
+//// Remove it after you'll update all mobile keys
+
+
 void dap_enc_sig_dilithium_set_type(enum DAP_DILITHIUM_SIGN_SECURITY type)
 {
     _dilithium_type = type;
@@ -80,19 +84,28 @@ size_t dap_enc_sig_dilithium_verify_sign(struct dap_enc_key * key, const void *
         log_it(L_ERROR, "bad signature size");
         return 0;
     }
-
-    return (dilithium_crypto_sign_open( (unsigned char *) msg, msg_size, (dilithium_signature_t *) signature, key->pub_key_data));
+    int l_ret = dilithium_crypto_sign_open( (unsigned char *) msg, msg_size, (dilithium_signature_t *) signature, key->pub_key_data);
+    log_it(L_WARNING,"Wrong signature, can't open with code %d", l_ret);
+    return l_ret>0? l_ret : 0;
 }
 
 void dap_enc_sig_dilithium_key_delete(struct dap_enc_key * key)
 {
-    if( key->priv_key_data && key->pub_key_data)
+    if( key->priv_key_data && key->pub_key_data){
         dilithium_private_and_public_keys_delete((dilithium_private_key_t *) key->priv_key_data,
             (dilithium_public_key_t *) key->pub_key_data);
-    else if ( key->pub_key_data )
+        free(key->pub_key_data);
+        free(key->priv_key_data);
+        key->pub_key_data=NULL;
+        key->priv_key_data=NULL;
+    }else if ( key->pub_key_data ){
         dilithium_public_key_delete((dilithium_public_key_t *) key->pub_key_data);
-    else if ( key->priv_key_data )
-        dilithium_public_key_delete((dilithium_public_key_t *) key->priv_key_data);
+        free(key->pub_key_data);
+        key->pub_key_data=NULL;
+    }else if ( key->priv_key_data ){
+        dilithium_private_key_delete((dilithium_private_key_t *) key->priv_key_data);
+        key->priv_key_data=NULL;
+    }
 
 }
 
@@ -114,12 +127,15 @@ uint8_t* dap_enc_dilithium_write_signature(dilithium_signature_t* a_sign, size_t
     size_t l_buflen = dap_enc_dilithium_calc_signagture_size(a_sign);
 
     uint8_t *l_buf = DAP_NEW_SIZE(uint8_t, l_buflen);
-    memcpy(l_buf, &l_buflen, sizeof(size_t));
-    l_shift_mem += sizeof(size_t);
+    if(! l_buf)
+        return NULL;
+
+    memcpy(l_buf, &l_buflen, sizeof(uint64_t));
+    l_shift_mem += sizeof(uint64_t);
     memcpy(l_buf + l_shift_mem, &a_sign->kind, sizeof(dilithium_kind_t));
     l_shift_mem += sizeof(dilithium_kind_t);
     memcpy(l_buf + l_shift_mem, &a_sign->sig_len, sizeof(unsigned long long));
-    l_shift_mem += sizeof(unsigned long long);
+    l_shift_mem += sizeof(uint64_t);
     memcpy(l_buf + l_shift_mem, a_sign->sig_data, a_sign->sig_len );
     l_shift_mem += a_sign->sig_len ;
 
@@ -131,12 +147,63 @@ uint8_t* dap_enc_dilithium_write_signature(dilithium_signature_t* a_sign, size_t
 /* Deserialize a signature */
 dilithium_signature_t* dap_enc_dilithium_read_signature(uint8_t *a_buf, size_t a_buflen)
 {
-    if( !a_buf || (a_buflen < (sizeof(size_t) + sizeof(dilithium_kind_t)) )  )
+    if (!a_buf){
+        log_it(L_ERROR,"::read_signature() NULL buffer on input");
+        return NULL;
+    }
+    if(a_buflen < (sizeof(uint64_t) + sizeof(dilithium_kind_t) + sizeof (uint64_t) )){
+        log_it(L_ERROR,"::read_signature() Buflen %zd is smaller than first three fields(%zd)", a_buflen,
+               sizeof(uint64_t) + sizeof(dilithium_kind_t) +sizeof (uint64_t)  );
+        return NULL;
+    }
+
+    dilithium_kind_t kind;
+    uint64_t l_buflen_internal = 0;
+    memcpy(&l_buflen_internal, a_buf, sizeof(uint64_t));
+    memcpy(&kind, a_buf + sizeof(uint64_t), sizeof(dilithium_kind_t));
+    if(l_buflen_internal != a_buflen)
+        return NULL ;
+    dilithium_param_t p;
+    if(!dilithium_params_init(&p, kind))
+        return NULL ;
+
+    dilithium_signature_t* l_sign = DAP_NEW(dilithium_signature_t);
+    l_sign->kind = kind;
+    uint64_t l_shift_mem = sizeof(uint64_t) + sizeof(dilithium_kind_t);
+    memcpy(&l_sign->sig_len, a_buf + l_shift_mem, sizeof(uint64_t));
+
+    if(   ( l_sign->sig_len> (UINT64_MAX - sizeof(uint64_t) + sizeof(dilithium_kind_t) +sizeof (uint64_t))) ||
+          ( a_buflen < (sizeof(uint64_t) + sizeof(dilithium_kind_t) +sizeof (uint64_t) + l_sign->sig_len ))
+       ){
+        log_it(L_ERROR,"::read_signature() Buflen %zd is smaller than all fields together(%zd)", a_buflen,
+               sizeof(uint64_t) + sizeof(dilithium_kind_t) + l_sign->sig_len  );
+        return NULL;
+    }
+
+
+    l_shift_mem += sizeof(uint64_t);
+    l_sign->sig_data = DAP_NEW_SIZE(unsigned char, l_sign->sig_len);
+    if (!l_sign->sig_data)
+        log_it(L_ERROR,"::read_signature() Can't allocate sig_data %zd size", l_sign->sig_len);
+    memcpy(l_sign->sig_data, a_buf + l_shift_mem, l_sign->sig_len);
+    l_shift_mem += l_sign->sig_len;
+    return l_sign;
+}
+
+/**
+ * @brief dap_enc_dilithium_read_signature
+ * @param a_buf
+ * @param a_buflen
+ * @return
+ */
+dilithium_signature_t* dap_enc_dilithium_read_signature_old(uint8_t *a_buf, size_t a_buflen)
+{
+    if( !a_buf || (a_buflen < (sizeof(uint32_t) + sizeof(dilithium_kind_t)) )  )
         return NULL ;
     dilithium_kind_t kind;
-    size_t l_buflen_internal = 0;
-    memcpy(&l_buflen_internal, a_buf, sizeof(size_t));
-    memcpy(&kind, a_buf + sizeof(size_t), sizeof(dilithium_kind_t));
+    uint32_t l_buflen_internal = 0;
+    memcpy(&l_buflen_internal, a_buf, sizeof(uint32_t));
+    memcpy(&kind, a_buf + sizeof(uint32_t), sizeof(dilithium_kind_t));
     if(l_buflen_internal != a_buflen)
         return NULL ;
     dilithium_param_t p;
@@ -145,7 +212,7 @@ dilithium_signature_t* dap_enc_dilithium_read_signature(uint8_t *a_buf, size_t a
 
     dilithium_signature_t* l_sign = DAP_NEW(dilithium_signature_t);
     l_sign->kind = kind;
-    size_t l_shift_mem = sizeof(size_t) + sizeof(dilithium_kind_t);
+    size_t l_shift_mem = sizeof(uint32_t) + sizeof(dilithium_kind_t);
     memcpy(&l_sign->sig_len, a_buf + l_shift_mem, sizeof(unsigned long long));
     l_shift_mem += sizeof(unsigned long long);
     l_sign->sig_data = DAP_NEW_SIZE(unsigned char, l_sign->sig_len);
@@ -154,6 +221,7 @@ dilithium_signature_t* dap_enc_dilithium_read_signature(uint8_t *a_buf, size_t a
     return l_sign;
 }
 
+
 /* Serialize a private key. */
 uint8_t* dap_enc_dilithium_write_private_key(const dilithium_private_key_t* a_private_key, size_t *a_buflen_out)
 {
@@ -161,11 +229,11 @@ uint8_t* dap_enc_dilithium_write_private_key(const dilithium_private_key_t* a_pr
     if(!dilithium_params_init(&p, a_private_key->kind))
         return NULL;
 
-    size_t l_buflen = sizeof(size_t) + sizeof(dilithium_kind_t) + p.CRYPTO_SECRETKEYBYTES; //CRYPTO_PUBLICKEYBYTES;
-    uint8_t *l_buf = DAP_NEW_SIZE(uint8_t, l_buflen);
-    memcpy(l_buf, &l_buflen, sizeof(size_t));
-    memcpy(l_buf + sizeof(size_t), &a_private_key->kind, sizeof(dilithium_kind_t));
-    memcpy(l_buf + sizeof(size_t) + sizeof(dilithium_kind_t), a_private_key->data, p.CRYPTO_SECRETKEYBYTES);
+    uint64_t l_buflen = sizeof(uint64_t) + sizeof(dilithium_kind_t) + p.CRYPTO_SECRETKEYBYTES; //CRYPTO_PUBLICKEYBYTES;
+    byte_t *l_buf = DAP_NEW_Z_SIZE(byte_t, l_buflen);
+    memcpy(l_buf, &l_buflen, sizeof(uint64_t));
+    memcpy(l_buf + sizeof(uint64_t), &a_private_key->kind, sizeof(dilithium_kind_t));
+    memcpy(l_buf + sizeof(uint64_t) + sizeof(dilithium_kind_t), a_private_key->data, p.CRYPTO_SECRETKEYBYTES);
     if(a_buflen_out)
         *a_buflen_out = l_buflen;
     return l_buf;
@@ -178,11 +246,11 @@ uint8_t* dap_enc_dilithium_write_public_key(const dilithium_public_key_t* a_publ
     if(!dilithium_params_init(&p, a_public_key->kind))
         return NULL;
 
-    size_t l_buflen = sizeof(size_t) + sizeof(dilithium_kind_t) + p.CRYPTO_PUBLICKEYBYTES;
-    uint8_t *l_buf = DAP_NEW_SIZE(uint8_t, l_buflen);
-    memcpy(l_buf, &l_buflen, sizeof(size_t));
-    memcpy(l_buf + sizeof(size_t), &a_public_key->kind, sizeof(dilithium_kind_t));
-    memcpy(l_buf + sizeof(size_t) + sizeof(dilithium_kind_t), a_public_key->data, p.CRYPTO_PUBLICKEYBYTES);
+    uint64_t l_buflen = sizeof(uint64_t) + sizeof(dilithium_kind_t) + p.CRYPTO_PUBLICKEYBYTES;
+    uint8_t *l_buf = DAP_NEW_Z_SIZE(byte_t, l_buflen);
+    memcpy(l_buf, &l_buflen, sizeof(uint64_t));
+    memcpy(l_buf + sizeof(uint64_t), &a_public_key->kind, sizeof(dilithium_kind_t));
+    memcpy(l_buf + sizeof(uint64_t) + sizeof(dilithium_kind_t), a_public_key->data, p.CRYPTO_PUBLICKEYBYTES);
     if(a_buflen_out)
         *a_buflen_out = l_buflen;
     return l_buf;
@@ -191,43 +259,155 @@ uint8_t* dap_enc_dilithium_write_public_key(const dilithium_public_key_t* a_publ
 /* Deserialize a private key. */
 dilithium_private_key_t* dap_enc_dilithium_read_private_key(const uint8_t *a_buf, size_t a_buflen)
 {
-    if(!a_buf || a_buflen < (sizeof(size_t) + sizeof(dilithium_kind_t)))
+    if(!a_buf ){
+        return NULL;
+    }
+
+    if(a_buflen < (sizeof(uint64_t) + sizeof(dilithium_kind_t))){
+        log_it(L_ERROR,"::read_private_key() Buflen %zd is smaller than first two fields(%zd)", a_buflen,sizeof(uint64_t) + sizeof(dilithium_kind_t)  );
+        return NULL;
+    }
+
+    dilithium_kind_t kind;
+    uint64_t l_buflen = 0;
+    memcpy(&l_buflen, a_buf, sizeof(uint64_t));
+    memcpy(&kind, a_buf + sizeof(uint64_t), sizeof(dilithium_kind_t));
+    if(l_buflen != a_buflen)
+        return NULL;
+    dilithium_param_t p;
+    if(!dilithium_params_init(&p, kind))
+        return NULL;
+
+    if(a_buflen < (sizeof(uint64_t) + sizeof(dilithium_kind_t) + p.CRYPTO_SECRETKEYBYTES ) ){
+        log_it(L_ERROR,"::read_private_key() Buflen %zd is smaller than all fields together(%zd)", a_buflen,
+               sizeof(uint64_t) + sizeof(dilithium_kind_t) + p.CRYPTO_SECRETKEYBYTES  );
+        return NULL;
+    }
+
+    dilithium_private_key_t* l_private_key = DAP_NEW(dilithium_private_key_t);
+    l_private_key->kind = kind;
+
+    l_private_key->data = DAP_NEW_SIZE(unsigned char, p.CRYPTO_SECRETKEYBYTES);
+    memcpy(l_private_key->data, a_buf + sizeof(uint64_t) + sizeof(dilithium_kind_t), p.CRYPTO_SECRETKEYBYTES);
+    return l_private_key;
+}
+
+/* Deserialize a private key. */
+dilithium_private_key_t* dap_enc_dilithium_read_private_key_old(const uint8_t *a_buf, size_t a_buflen)
+{
+    if(!a_buf || a_buflen < (sizeof(uint32_t) + sizeof(dilithium_kind_t)))
         return NULL;
     dilithium_kind_t kind;
-    size_t l_buflen = 0;
-    memcpy(&l_buflen, a_buf, sizeof(size_t));
-    memcpy(&kind, a_buf + sizeof(size_t), sizeof(dilithium_kind_t));
+    uint32_t l_buflen = 0;
+    memcpy(&l_buflen, a_buf, sizeof(uint32_t));
+    memcpy(&kind, a_buf + sizeof(uint32_t), sizeof(dilithium_kind_t));
     if(l_buflen != a_buflen)
         return NULL;
     dilithium_param_t p;
     if(!dilithium_params_init(&p, kind))
         return NULL;
+    if(a_buflen < (sizeof(uint64_t) + sizeof(dilithium_kind_t) + p.CRYPTO_SECRETKEYBYTES ) ){
+        log_it(L_ERROR,"::read_private_key() Buflen %zd is smaller than all fields together(%zd)", a_buflen,
+               sizeof(uint64_t) + sizeof(dilithium_kind_t) + p.CRYPTO_SECRETKEYBYTES  );
+        return NULL;
+    }
+
     dilithium_private_key_t* l_private_key = DAP_NEW(dilithium_private_key_t);
     l_private_key->kind = kind;
 
     l_private_key->data = DAP_NEW_SIZE(unsigned char, p.CRYPTO_SECRETKEYBYTES);
-    memcpy(l_private_key->data, a_buf + sizeof(size_t) + sizeof(dilithium_kind_t), p.CRYPTO_SECRETKEYBYTES);
+    memcpy(l_private_key->data, a_buf + sizeof(uint32_t) + sizeof(dilithium_kind_t), p.CRYPTO_SECRETKEYBYTES);
     return l_private_key;
 }
 
 /* Deserialize a public key. */
 dilithium_public_key_t* dap_enc_dilithium_read_public_key(const uint8_t *a_buf, size_t a_buflen)
 {
-    if(!a_buf || a_buflen < (sizeof(size_t) + sizeof(dilithium_kind_t)))
+    if (!a_buf){
+        log_it(L_ERROR,"::read_public_key() NULL buffer on input");
+        return NULL;
+    }
+    if(a_buflen < (sizeof(uint64_t) + sizeof(dilithium_kind_t))){
+        log_it(L_ERROR,"::read_public_key() Buflen %zd is smaller than first two fields(%zd)", a_buflen,sizeof(uint64_t) + sizeof(dilithium_kind_t)  );
+        return NULL;
+    }
+    dilithium_kind_t kind = 0;
+    uint64_t l_buflen = 0;
+    memcpy(&l_buflen, a_buf, sizeof(uint64_t));
+    memcpy(&kind, a_buf + sizeof(uint64_t), sizeof(dilithium_kind_t));
+    if(l_buflen != a_buflen){
+        log_it(L_ERROR,"::read_public_key() Buflen field inside buffer is %u when expected to be %u", l_buflen, a_buflen);
+        return NULL;
+    }
+    dilithium_param_t p;
+    if(!dilithium_params_init(&p, kind)){
+        log_it(L_ERROR,"::read_public_key() Can't find params for signature kind %d", kind);
+        return NULL;
+    }
+
+    if(a_buflen < (sizeof(uint64_t) + sizeof(dilithium_kind_t) + p.CRYPTO_PUBLICKEYBYTES ) ){
+        log_it(L_ERROR,"::read_public_key() Buflen %zd is smaller than all fields together(%zd)", a_buflen,
+               sizeof(uint64_t) + sizeof(dilithium_kind_t) + p.CRYPTO_PUBLICKEYBYTES  );
         return NULL;
+    }
+
+    dilithium_public_key_t* l_public_key = DAP_NEW_Z(dilithium_public_key_t);
+    if (!l_public_key){
+        log_it(L_CRITICAL,"::read_public_key() Can't allocate memory for public key");
+        return NULL;
+    }
+    l_public_key->kind = kind;
+
+    l_public_key->data = DAP_NEW_Z_SIZE(byte_t, p.CRYPTO_PUBLICKEYBYTES);
+    if (!l_public_key->data){
+        log_it(L_CRITICAL,"::read_public_key() Can't allocate memory for public key's data");
+        DAP_DELETE(l_public_key);
+        return NULL;
+    }
+
+    memcpy(l_public_key->data, a_buf + sizeof(uint64_t) + sizeof(dilithium_kind_t), p.CRYPTO_PUBLICKEYBYTES);
+    return l_public_key;
+}
+
+/**
+ * @brief dap_enc_dilithium_read_public_key_old
+ * @param a_buf
+ * @param a_buflen
+ * @return
+ */
+dilithium_public_key_t* dap_enc_dilithium_read_public_key_old(const uint8_t *a_buf, size_t a_buflen)
+{
+    if (!a_buf){
+        log_it(L_ERROR,"::read_public_key() NULL buffer on input");
+        return NULL;
+    }
+    if(a_buflen < (sizeof(uint64_t) + sizeof(dilithium_kind_t))){
+        log_it(L_ERROR,"::read_public_key() Buflen %zd is smaller than first two fields(%zd)", a_buflen,sizeof(uint64_t) + sizeof(dilithium_kind_t)  );
+        return NULL;
+    }
+
     dilithium_kind_t kind;
-    size_t l_buflen = 0;
-    memcpy(&l_buflen, a_buf, sizeof(size_t));
-    memcpy(&kind, a_buf + sizeof(size_t), sizeof(dilithium_kind_t));
+    uint32_t l_buflen = 0;
+    memcpy(&l_buflen, a_buf, sizeof(uint32_t));
+    memcpy(&kind, a_buf + sizeof(uint32_t), sizeof(dilithium_kind_t));
     if(l_buflen != a_buflen)
         return NULL;
     dilithium_param_t p;
-    if(!dilithium_params_init(&p, kind))
+    if(!dilithium_params_init(&p, kind)){
+        log_it(L_ERROR,"::read_public_key() Can't find params for signature kind %d", kind);
+        return NULL;
+    }
+
+    if(a_buflen < (sizeof(uint64_t) + sizeof(dilithium_kind_t) + p.CRYPTO_PUBLICKEYBYTES ) ){
+        log_it(L_ERROR,"::read_public_key_old() Buflen %zd is smaller than all fields together(%zd)", a_buflen,
+               sizeof(uint64_t) + sizeof(dilithium_kind_t) + p.CRYPTO_PUBLICKEYBYTES  );
         return NULL;
+    }
+
     dilithium_public_key_t* l_public_key = DAP_NEW_Z(dilithium_public_key_t);
     l_public_key->kind = kind;
 
     l_public_key->data = DAP_NEW_Z_SIZE(unsigned char, p.CRYPTO_PUBLICKEYBYTES);
-    memcpy(l_public_key->data, a_buf + sizeof(size_t) + sizeof(dilithium_kind_t), p.CRYPTO_PUBLICKEYBYTES);
+    memcpy(l_public_key->data, a_buf + sizeof(uint32_t) + sizeof(dilithium_kind_t), p.CRYPTO_PUBLICKEYBYTES);
     return l_public_key;
 }
diff --git a/dap-sdk/crypto/src/dap_enc_key.c b/dap-sdk/crypto/src/dap_enc_key.c
index a04f827079a692449a16d1f796f1117295b0905e..580127163d885d223b3d0857a501dde984c170f7 100755
--- a/dap-sdk/crypto/src/dap_enc_key.c
+++ b/dap-sdk/crypto/src/dap_enc_key.c
@@ -550,6 +550,62 @@ int dap_enc_key_deserealize_priv_key(dap_enc_key_t *a_key, const uint8_t *a_buf,
     return 0;
 }
 
+int dap_enc_key_deserealize_pub_key_old(dap_enc_key_t *a_key, const uint8_t *a_buf, size_t a_buflen)
+{
+    if(!a_key || !a_buf)
+        return -1;
+    switch (a_key->type) {
+    case DAP_ENC_KEY_TYPE_SIG_BLISS:
+        if((a_key->pub_key_data)) {
+            bliss_b_public_key_delete((bliss_public_key_t *) a_key->pub_key_data);
+            DAP_DELETE(a_key->pub_key_data);
+        }
+        a_key->pub_key_data = (uint8_t*) dap_enc_sig_bliss_read_public_key(a_buf, a_buflen);
+        if(!a_key->pub_key_data)
+        {
+            a_key->pub_key_data_size = 0;
+            return -1;
+        }
+        a_key->pub_key_data_size = sizeof(bliss_public_key_t);
+        break;
+    case DAP_ENC_KEY_TYPE_SIG_TESLA:
+        tesla_public_key_delete((tesla_public_key_t *) a_key->pub_key_data);
+        a_key->pub_key_data = (uint8_t*) dap_enc_tesla_read_public_key(a_buf, a_buflen);
+        if(!a_key->pub_key_data)
+        {
+            a_key->pub_key_data_size = 0;
+            return -1;
+        }
+        a_key->pub_key_data_size = sizeof(tesla_public_key_t);
+        break;
+    case DAP_ENC_KEY_TYPE_SIG_PICNIC:
+        DAP_DELETE(a_key->pub_key_data);
+        a_key->pub_key_data_size = a_buflen;
+        a_key->pub_key_data = DAP_NEW_Z_SIZE(uint8_t, a_key->pub_key_data_size);
+        memcpy(a_key->pub_key_data, a_buf, a_key->pub_key_data_size);
+        dap_enc_sig_picnic_update(a_key);
+        break;
+    case DAP_ENC_KEY_TYPE_SIG_DILITHIUM:
+        if ( a_key->pub_key_data )
+            dilithium_public_key_delete((dilithium_public_key_t *) a_key->pub_key_data);
+        a_key->pub_key_data = (uint8_t*) dap_enc_dilithium_read_public_key_old(a_buf, a_buflen);
+        if(!a_key->pub_key_data)
+        {
+            a_key->pub_key_data_size = 0;
+            return -1;
+        }
+        a_key->pub_key_data_size = sizeof(dilithium_public_key_t);
+        break;
+    default:
+        DAP_DELETE(a_key->pub_key_data);
+        a_key->pub_key_data_size = a_buflen;
+        a_key->pub_key_data = DAP_NEW_Z_SIZE(uint8_t, a_key->pub_key_data_size);
+        memcpy(a_key->pub_key_data, a_buf, a_key->pub_key_data_size);
+    }
+    return 0;
+
+}
+
 /**
  * @brief dap_enc_key_deserealize_pub_key
  *
@@ -596,6 +652,7 @@ int dap_enc_key_deserealize_pub_key(dap_enc_key_t *a_key, const uint8_t *a_buf,
     case DAP_ENC_KEY_TYPE_SIG_DILITHIUM:
         if ( a_key->pub_key_data )
             dilithium_public_key_delete((dilithium_public_key_t *) a_key->pub_key_data);
+
         a_key->pub_key_data = (uint8_t*) dap_enc_dilithium_read_public_key(a_buf, a_buflen);
         if(!a_key->pub_key_data)
         {
diff --git a/dap-sdk/crypto/src/sig_dilithium/dilithium_params.c b/dap-sdk/crypto/src/sig_dilithium/dilithium_params.c
index ba5391535cc10e1de813a6a348ffb83b0f9fe330..fa3abe282b5dfc8c2a028989eb1e1e7cf32d8cda 100755
--- a/dap-sdk/crypto/src/sig_dilithium/dilithium_params.c
+++ b/dap-sdk/crypto/src/sig_dilithium/dilithium_params.c
@@ -92,7 +92,8 @@ static const dilithium_param_t dilithium_params[] = {
 };
 
 bool dilithium_params_init(dilithium_param_t *params, dilithium_kind_t kind){
-  assert(params != NULL);
+  if(!params)
+      return false;
 
   memset(params, 0, sizeof(dilithium_param_t));
   
diff --git a/dap-sdk/crypto/src/sig_dilithium/dilithium_params.h b/dap-sdk/crypto/src/sig_dilithium/dilithium_params.h
index b7294dea8d2e32bc68acc1714c9dcfc20e995c0f..135a77e2ee8dbd86683baa81c4cf8f59c55e1241 100755
--- a/dap-sdk/crypto/src/sig_dilithium/dilithium_params.h
+++ b/dap-sdk/crypto/src/sig_dilithium/dilithium_params.h
@@ -27,7 +27,7 @@
 
 ///========================================================================
 /* Names for the four varieties of Dilithium */
-typedef enum { MODE_0, MODE_1, MODE_2, MODE_3 } dilithium_kind_t;
+typedef enum { MODE_0, MODE_1, MODE_2, MODE_3 } __attribute__((aligned(4))) dilithium_kind_t;
 
 typedef struct {
   dilithium_kind_t kind;     /* the kind of Dilithium (i.e. *this* choice of parameters)  */
@@ -67,7 +67,7 @@ typedef struct {
 typedef struct {
   dilithium_kind_t kind;                      /* the kind of dilithium       */
   unsigned char *sig_data;
-  unsigned long long sig_len;
+  uint64_t sig_len;
 } dilithium_signature_t;
 
 
diff --git a/dap-sdk/crypto/src/sig_dilithium/dilithium_sign.c b/dap-sdk/crypto/src/sig_dilithium/dilithium_sign.c
index 47942fa5ec7986bbccc589ee802960da3ebb6ec5..fbc106caca8d6eeae954241ce31f0be0d59e1cc4 100755
--- a/dap-sdk/crypto/src/sig_dilithium/dilithium_sign.c
+++ b/dap-sdk/crypto/src/sig_dilithium/dilithium_sign.c
@@ -211,8 +211,8 @@ int dilithium_crypto_sign( dilithium_signature_t *sig, const unsigned char *m, u
 
     unsigned long long i, j;
     unsigned int n;
-    unsigned char seedbuf[2*SEEDBYTES + CRHBYTES];
-    unsigned char tr[CRHBYTES];
+    byte_t seedbuf[2*SEEDBYTES + CRHBYTES]={0};
+    byte_t tr[CRHBYTES]={0};
     unsigned char *rho, *key, *mu;
     uint16_t nonce = 0;
     poly c, chat;
@@ -318,17 +318,18 @@ int dilithium_crypto_sign( dilithium_signature_t *sig, const unsigned char *m, u
 /*************************************************/
 int dilithium_crypto_sign_open( unsigned char *m, unsigned long long mlen, dilithium_signature_t *sig, const dilithium_public_key_t * public_key)
 {
-    assert(public_key->kind == sig->kind);
+    if(public_key->kind != sig->kind)
+        return -1;
 
     dilithium_param_t *p = malloc(sizeof(dilithium_param_t));
     if (! dilithium_params_init( p, public_key->kind)) {
         free(p);
-        return -1;
+        return -2;
     }
 
     if (sig->sig_len < p->CRYPTO_BYTES ) {
         free(p);
-        return -1;
+        return -3;
     }
 
     unsigned long long i;
@@ -340,18 +341,18 @@ int dilithium_crypto_sign_open( unsigned char *m, unsigned long long mlen, dilit
 
     if((sig->sig_len - p->CRYPTO_BYTES) != mlen) {
         free(p);
-        return -1;
+        return -4;
     }
 
     dilithium_unpack_pk(rho, &t1, public_key->data, p);
     if(dilithium_unpack_sig(&z, &h, &c, sig->sig_data, p)) {
         free(p);
-        return -1;
+        return -5;
     }
 
     if(polyvecl_chknorm(&z, GAMMA1 - p->PARAM_BETA, p)) {
         free(p);
-        return -1;
+        return -6;
     }
 
     unsigned char *tmp_m = malloc(CRHBYTES + mlen);
@@ -388,7 +389,7 @@ int dilithium_crypto_sign_open( unsigned char *m, unsigned long long mlen, dilit
     for(i = 0; i < NN; ++i)
         if(c.coeffs[i] != cp.coeffs[i]) {
             free(p);
-            return -1;
+            return -7;
         }
 
     return 0;
diff --git a/dap-sdk/net/client/dap_client_http.c b/dap-sdk/net/client/dap_client_http.c
index bc66333e38aa96eeb89bd388f95eef9c97155fad..4b2bb2d16a86c6141fce289e24b262f041326c9f 100644
--- a/dap-sdk/net/client/dap_client_http.c
+++ b/dap-sdk/net/client/dap_client_http.c
@@ -368,14 +368,17 @@ void* dap_client_http_request_custom(dap_worker_t * a_worker,const char *a_uplin
 #ifdef DAP_OS_WINDOWS
     SOCKET l_socket = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
     if (l_socket == INVALID_SOCKET) {
-        log_it(L_ERROR, "Socket create error: %d", WSAGetLastError());
+        int err = WSAGetLastError();
+        log_it(L_ERROR, "Socket create error: %d", err);
+        if(a_error_callback)
+            a_error_callback(err, a_obj);
 #else
     int l_socket = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
     if (l_socket == -1) {
         log_it(L_ERROR, "Error %d with socket create", errno);
-#endif
         if(a_error_callback)
             a_error_callback(errno,a_obj);
+#endif
         return NULL;
     }
     // Get socket flags
@@ -486,12 +489,15 @@ void* dap_client_http_request_custom(dap_worker_t * a_worker,const char *a_uplin
             log_it(L_DEBUG, "Connecting to %s:%u", a_uplink_addr, a_uplink_port);
             l_http_pvt->worker = a_worker?a_worker: dap_events_worker_get_auto();
             dap_worker_add_events_socket(l_ev_socket,l_http_pvt->worker);
+            dap_timerfd_start_on_worker(l_http_pvt->worker,s_client_timeout_ms, s_timer_timeout_check,l_ev_socket);
             return l_http_pvt;
         } else {
             log_it(L_ERROR, "Socket %d connecting error: %d", l_ev_socket->socket, l_err2);
             s_client_http_delete( l_http_pvt);
             l_ev_socket->_inheritor = NULL;
             dap_events_socket_delete_unsafe( l_ev_socket, true);
+            if(a_error_callback)
+                a_error_callback(l_err2, a_obj);
             return NULL;
         }
     }
@@ -509,6 +515,7 @@ void* dap_client_http_request_custom(dap_worker_t * a_worker,const char *a_uplin
         strerror_r(l_err, l_errbuf, sizeof (l_errbuf));
         log_it(L_ERROR, "Connecting error: \"%s\" (code %d)", l_errbuf, l_err);
         s_client_http_delete( l_http_pvt);
+        l_ev_socket->_inheritor = NULL;
         dap_events_socket_delete_unsafe( l_ev_socket, true);
         if(a_error_callback)
             a_error_callback(errno,a_obj);
diff --git a/dap-sdk/net/core/dap_events_socket.c b/dap-sdk/net/core/dap_events_socket.c
index 8e5a2ccb17e4c717696df17e7dd05d8e8cab6c77..2d7366689cf8b9363f472137d98a1cc04309e7ab 100644
--- a/dap-sdk/net/core/dap_events_socket.c
+++ b/dap-sdk/net/core/dap_events_socket.c
@@ -163,11 +163,7 @@ dap_events_socket_t *dap_events_socket_wrap_no_add( dap_events_t *a_events,
 
     if ( a_sock!= 0 && a_sock != -1){
         pthread_rwlock_wrlock(&a_events->sockets_rwlock);
-#ifdef DAP_OS_WINDOWS
-        HASH_ADD(hh,a_events->sockets, socket, sizeof(SOCKET), ret);
-#else
         HASH_ADD_INT(a_events->sockets, socket, ret);
-#endif
         pthread_rwlock_unlock(&a_events->sockets_rwlock);
     }else
         log_it(L_WARNING, "Be carefull, you've wrapped socket 0 or -1 so it wasn't added to global list. Do it yourself when possible");
@@ -1224,11 +1220,7 @@ dap_events_socket_t * dap_events_socket_wrap2( dap_server_t *a_server, struct da
   ret->last_time_active = ret->last_ping_request = time( NULL );
 
   pthread_rwlock_wrlock( &a_events->sockets_rwlock );
-#ifdef DAP_OS_WINDOWS
-  HASH_ADD(hh,a_events->sockets, socket, sizeof(SOCKET), ret);
-#else
   HASH_ADD_INT(a_events->sockets, socket, ret);
-#endif
   pthread_rwlock_unlock( &a_events->sockets_rwlock );
 
   return ret;
@@ -1249,14 +1241,9 @@ dap_events_socket_t *dap_events_socket_find_unsafe( int sock, struct dap_events
         return NULL;
     if(a_events->sockets) {
         pthread_rwlock_rdlock(&a_events->sockets_rwlock);
-#ifdef DAP_OS_WINDOWS
-        HASH_FIND(hh, a_events->sockets, &sock, sizeof(SOCKET), ret );
-#else
         HASH_FIND_INT( a_events->sockets, &sock, ret );
-#endif
         pthread_rwlock_unlock(&a_events->sockets_rwlock);
     }
-
     return ret;
 }
 
@@ -1367,8 +1354,7 @@ void dap_events_socket_remove_and_delete_unsafe( dap_events_socket_t *a_es, bool
         return;
 
     //log_it( L_DEBUG, "es is going to be removed from the lists and free the memory (0x%016X)", a_es );
-    if ( a_es->worker)
-        dap_events_socket_remove_from_worker_unsafe(a_es, a_es->worker);
+    dap_events_socket_remove_from_worker_unsafe(a_es, a_es->worker);
 
     //log_it( L_DEBUG, "dap_events_socket wrapped around %d socket is removed", a_es->socket );
 
@@ -1387,7 +1373,11 @@ void dap_events_socket_delete_unsafe( dap_events_socket_t * a_esocket , bool a_p
 {
     if (a_esocket->events){ // It could be socket NOT from events
         if(!dap_events_socket_find_unsafe(a_esocket->socket, a_esocket->events)){
-            log_it( L_ERROR, "dap_events_socket 0x%x already deleted", a_esocket);
+            log_it(L_ERROR, "esocket %d type %d already deleted", a_esocket->socket, a_esocket->type);
+            /*dap_events_socket_t * es1 = NULL, *es2;
+              HASH_ITER(hh, a_esocket->events->sockets, es1, es2) {
+                log_it(L_INFO, "Table: socket %d", es1->socket);
+            }*/
             return ;
         }
 
@@ -1404,12 +1394,14 @@ void dap_events_socket_delete_unsafe( dap_events_socket_t * a_esocket , bool a_p
     DAP_DEL_Z(a_esocket->_pvt)
     DAP_DEL_Z(a_esocket->buf_in)
     DAP_DEL_Z(a_esocket->buf_out)
-    DAP_DEL_Z(a_esocket->remote_addr_str)
+    if (a_esocket->type == DESCRIPTOR_TYPE_SOCKET) {
+        DAP_DEL_Z(a_esocket->remote_addr_str)
+    }
 #ifdef DAP_OS_WINDOWS
-    if ( a_esocket->socket && a_esocket->socket != INVALID_SOCKET) {
+    if ( a_esocket->socket && (a_esocket->socket != INVALID_SOCKET)) {
         closesocket( a_esocket->socket );
 #else
-        if ( a_esocket->socket && a_esocket->socket != -1) {
+        if ( a_esocket->socket && (a_esocket->socket != -1)) {
         close( a_esocket->socket );
 #ifdef DAP_EVENTS_CAPS_QUEUE_PIPE2
         if( a_esocket->type == DESCRIPTOR_TYPE_QUEUE){
@@ -1429,7 +1421,7 @@ void dap_events_socket_delete_unsafe( dap_events_socket_t * a_esocket , bool a_p
 void dap_events_socket_remove_from_worker_unsafe( dap_events_socket_t *a_es, dap_worker_t * a_worker)
 {
     if (!a_es->worker) {
-        // Socket already removed from worker
+        log_it(L_INFO, "No worker assigned to esocket %d", a_es->socket);
         return;
     }
 #ifdef DAP_EVENTS_CAPS_EPOLL
diff --git a/dap-sdk/net/core/dap_worker.c b/dap-sdk/net/core/dap_worker.c
index a716e96214d1f39dc057abda93b204dedad79604..5af2270c93503bdba7cd590685813865a082af1d 100644
--- a/dap-sdk/net/core/dap_worker.c
+++ b/dap-sdk/net/core/dap_worker.c
@@ -180,6 +180,10 @@ void *dap_worker_thread(void *arg)
             l_flag_nval     = false;
 #elif defined ( DAP_EVENTS_CAPS_POLL)
             short l_cur_events =l_worker->poll[n].revents;
+
+            if (l_worker->poll[n].fd == -1) // If it was deleted on previous iterations
+                continue;
+
             if (!l_cur_events) // No events for this socket
                 continue;
             l_flag_hup =  l_cur_events& POLLHUP;
@@ -632,10 +636,12 @@ void *dap_worker_thread(void *arg)
             if ((l_cur->flags & DAP_SOCK_SIGNAL_CLOSE) && !l_cur->no_close)
             {
                 if (l_cur->buf_out_size == 0) {
-                    log_it(L_INFO, "Process signal to close %s, sock %u [thread %u]", l_cur->remote_addr_str, l_cur->socket, l_tn);
+                    log_it(L_INFO, "Process signal to close %s sock %u type %d [thread %u]",
+                           l_cur->remote_addr_str ? l_cur->remote_addr_str : "", l_cur->socket, l_cur->type, l_tn);
                     dap_events_socket_remove_and_delete_unsafe( l_cur, false);
                 } else if (l_cur->buf_out_size ) {
-                    log_it(L_INFO, "Got signal to close %s, sock %u [thread %u] but buffer is not empty(%zd)", l_cur->remote_addr_str, l_cur->socket, l_tn,
+                    log_it(L_INFO, "Got signal to close %s sock %u [thread %u] type %d but buffer is not empty(%zd)",
+                           l_cur->remote_addr_str ? l_cur->remote_addr_str : "", l_cur->socket, l_cur->type, l_tn,
                            l_cur->buf_out_size);
                 }
             }
@@ -644,6 +650,7 @@ void *dap_worker_thread(void *arg)
                 log_it(L_NOTICE,"Worker :%u finished", l_worker->id);
                 return NULL;
             }
+
         }
 #ifdef DAP_EVENTS_CAPS_POLL
       /***********************************************************/
diff --git a/dap-sdk/net/core/include/dap_worker.h b/dap-sdk/net/core/include/dap_worker.h
index 4447b5f84b49f7bacb28ae157f06324b53bf4771..a88a9e459913207d89365ceec55f25d8ad8834bc 100644
--- a/dap-sdk/net/core/include/dap_worker.h
+++ b/dap-sdk/net/core/include/dap_worker.h
@@ -43,6 +43,7 @@ typedef struct dap_worker
 
     // Signal to exit
     bool signal_exit;
+
     // worker control queues
     dap_events_socket_t * queue_es_new; // Queue socket for new socket
     dap_events_socket_t ** queue_es_new_input; // Queue socket for new socket
diff --git a/modules/net/dap_chain_net.c b/modules/net/dap_chain_net.c
index e1523f1edb7e0299eb256f663b86473d7221dee3..402ca840b7b948347ebc0741d98d0decf7df2423 100644
--- a/modules/net/dap_chain_net.c
+++ b/modules/net/dap_chain_net.c
@@ -195,6 +195,9 @@ static void s_node_link_callback_stage(dap_chain_node_client_t * a_node_client,d
 static void s_node_link_callback_error(dap_chain_node_client_t * a_node_client, int a_error, void * a_arg);
 
 static bool s_net_states_proc(dap_proc_thread_t *a_thread, void *a_arg);
+static void s_net_state_link_prepare_success(dap_worker_t * a_worker,dap_chain_node_info_t * a_node_info, void * a_arg);
+static void s_net_state_link_prepare_error(dap_worker_t * a_worker,dap_chain_node_info_t * a_node_info, void * a_arg, int a_errno);
+
 
 
 
@@ -371,7 +374,7 @@ static void s_fill_links_from_root_aliases(dap_chain_net_t * a_net)
 {
      dap_chain_net_pvt_t *l_pvt_net = PVT(a_net);
      uint64_t l_own_addr = dap_chain_net_get_cur_addr_int(a_net);
-     for (int i = 0; i < MIN(s_max_links_count, l_pvt_net->seed_aliases_count); i++) {
+     for (size_t i = 0; i < MIN(s_max_links_count, l_pvt_net->seed_aliases_count); i++) {
          if (dap_list_length(l_pvt_net->links_info) >= s_max_links_count) {
              break;
          }
@@ -433,6 +436,38 @@ static void s_node_link_callback_error(dap_chain_node_client_t * a_node_client,
 
 }
 
+/**
+ * @brief s_net_state_link_prepare_success
+ * @param a_worker
+ * @param a_node_info
+ * @param a_arg
+ */
+static void s_net_state_link_prepare_success(dap_worker_t * a_worker,dap_chain_node_info_t * a_node_info, void * a_arg)
+{
+    if (a_link_node_info->hdr.address.uint64 != l_own_addr) {
+        l_pvt_net->links_info = dap_list_append(l_pvt_net->links_info, l_link_node_info);
+        l_tries = 0;
+    }
+    }
+    if (l_pvt_net->state_target == NET_STATE_OFFLINE) {
+        break;
+    }
+    l_tries++;
+    }
+    s_fill_links_from_root_aliases(l_net);
+}
+
+/**
+ * @brief s_net_state_link_prepare_error
+ * @param a_worker
+ * @param a_node_info
+ * @param a_arg
+ * @param a_errno
+ */
+static void s_net_state_link_prepare_error(dap_worker_t * a_worker,dap_chain_node_info_t * a_node_info, void * a_arg, int a_errno)
+{
+
+}
 
 /**
  * @brief s_net_states_proc
@@ -505,6 +540,7 @@ static bool s_net_states_proc(dap_proc_thread_t *a_thread, void *a_arg)
                     // Get DNS request result from root nodes as synchronization links
                     int l_max_tries = 5;
                     int l_tries = 0;
+                    bool l_sync_fill_root_nodes = true;
                     while (dap_list_length(l_pvt_net->links_info) < s_max_links_count && l_tries < l_max_tries) {
                         struct in_addr l_addr = {};
                         uint16_t i, l_port;
@@ -527,24 +563,29 @@ static bool s_net_states_proc(dap_proc_thread_t *a_thread, void *a_arg)
                         }
                         if (l_addr.s_addr) {
                             dap_chain_node_info_t *l_link_node_info = DAP_NEW_Z(dap_chain_node_info_t);
+                            if(! l_link_node_info){
+                                log_it(L_CRITICAL,"Can't allocate memory for node link info");
+                                break;
+                            }
 #ifdef DAP_OS_UNIX
                             struct in_addr _in_addr = { .s_addr = l_addr.s_addr  };
 #else
                             struct in_addr _in_addr = { { .S_addr = l_addr.S_un.S_addr } };
 #endif
                             log_it(L_INFO, "dns get addrs %s : %d, net %s", inet_ntoa(_in_addr), l_port, l_net->pub.name);
-                            int l_res = dap_dns_client_get_addr(l_addr, l_port, l_net->pub.name, l_link_node_info);
-                            if (!l_res && l_link_node_info->hdr.address.uint64 != l_own_addr) {
-                                l_pvt_net->links_info = dap_list_append(l_pvt_net->links_info, l_link_node_info);
-                                l_tries = 0;
-                            }
+                            l_sync_fill_root_nodes = false;
+                            dap_chain_node_info_dns_request(l_addr, l_port, l_net->pub.name, l_link_node_info,
+                                                                s_net_state_link_prepare_success,s_net_state_link_prepare_error,l_net);
+
+                            break;
                         }
                         if (l_pvt_net->state_target == NET_STATE_OFFLINE) {
                             break;
                         }
                         l_tries++;
                     }
-                    s_fill_links_from_root_aliases(l_net);
+                    if (l_sync_fill_root_nodes)
+                        s_fill_links_from_root_aliases(l_net);
                 } break;
             }
             if (l_pvt_net->state_target != NET_STATE_OFFLINE) {
diff --git a/modules/net/dap_chain_node_dns_client.c b/modules/net/dap_chain_node_dns_client.c
index c73b1508688369905bfba6a1f2f517eecd2197e8..21dc8bd1bc190e6fc829e7ae8811c51d39017066 100644
--- a/modules/net/dap_chain_node_dns_client.c
+++ b/modules/net/dap_chain_node_dns_client.c
@@ -37,6 +37,10 @@ struct dns_client
     struct in_addr addr;
     uint16_t port;
     char *name;
+    dap_dns_buf_t * dns_request;
+    byte_t * buf;
+    size_t buf_size;
+
     dap_dns_client_node_info_request_success_callback_t callback_success;
     dap_dns_client_node_info_request_error_callback_t callback_error;
     void * callbacks_arg;
@@ -49,16 +53,6 @@ static void s_dns_client_esocket_error_callback(dap_events_socket_t * a_esocket,
 static bool s_dns_client_esocket_timeout_callback( void * a_arg);
 static void s_dns_client_esocket_delete_callback(dap_events_socket_t * a_esocket, void * a_arg);
 
-/**
- * @brief s_dns_client_esocket_new_callback
- * @param a_esocket
- * @param a_arg
- */
-static void s_dns_client_esocket_new_callback(dap_events_socket_t * a_esocket, void * a_arg)
-{
-    struct dns_client * l_dns_client = (struct dns_client*) a_esocket->_inheritor;
-}
-
 /**
  * @brief s_dns_client_esocket_read_callback
  * @param a_esocket
@@ -66,40 +60,47 @@ static void s_dns_client_esocket_new_callback(dap_events_socket_t * a_esocket, v
  */
 static void s_dns_client_esocket_read_callback(dap_events_socket_t * a_esocket, void * a_arg)
 {
+    (void) a_arg;
     struct dns_client * l_dns_client = (struct dns_client*) a_esocket->_inheritor;
-    struct sockaddr_in l_clientaddr;
-    socklen_t l_clientlen = sizeof(l_clientaddr);
-    size_t l_recieved = recvfrom(l_sock, (char *)l_buf, l_buf_size, 0, (struct sockaddr *)&l_clientaddr, &l_clientlen);
-    size_t l_addr_point = DNS_HEADER_SIZE + strlen(a_name) + 2 + 2 * sizeof(uint16_t) + DNS_ANSWER_SIZE - sizeof(uint32_t);
+    byte_t * l_buf = a_esocket->buf_in;
+    size_t l_recieved = a_esocket->buf_in_size;
+    size_t l_addr_point = DNS_HEADER_SIZE + strlen(l_dns_client->name) + 2 + 2 * sizeof(uint16_t) + DNS_ANSWER_SIZE - sizeof(uint32_t);
     if (l_recieved < l_addr_point + sizeof(uint32_t)) {
         log_it(L_WARNING, "DNS answer incomplete");
-        closesocket(l_sock);
-        return -5;
+        l_dns_client->callback_error(a_esocket->worker, l_dns_client->result,l_dns_client->callbacks_arg,EREMOTEIO );
+        l_dns_client->is_callbacks_called = true;
+        a_esocket->flags |= DAP_SOCK_SIGNAL_CLOSE;
+        return;
     }
-    l_cur = l_buf + 3 * sizeof(uint16_t);
+    byte_t * l_cur = l_buf + 3 * sizeof(uint16_t);
     int l_answers_count = ntohs(*(uint16_t *)l_cur);
     if (l_answers_count != 1) {
         log_it(L_WARNING, "Incorrect DNS answer format");
-        closesocket(l_sock);
-        return -6;
+        l_dns_client->callback_error(a_esocket->worker, l_dns_client->result,l_dns_client->callbacks_arg,EMEDIUMTYPE );
+        l_dns_client->is_callbacks_called = true;
+        a_esocket->flags |= DAP_SOCK_SIGNAL_CLOSE;
+        return;
     }
     l_cur = l_buf + l_addr_point;
-    if (a_result) {
-        a_result->hdr.ext_addr_v4.s_addr = ntohl(*(uint32_t *)l_cur);
+    if ( l_dns_client->result) {
+        l_dns_client->result->hdr.ext_addr_v4.s_addr = ntohl(*(uint32_t *)l_cur);
     }
     l_cur = l_buf + 5 * sizeof(uint16_t);
     int l_additions_count = ntohs(*(uint16_t *)l_cur);
     if (l_additions_count == 1) {
         l_cur = l_buf + l_addr_point + DNS_ANSWER_SIZE;
-        if (a_result) {
-            a_result->hdr.ext_port = ntohs(*(uint16_t *)l_cur);
+        if (l_dns_client->result) {
+            l_dns_client->result->hdr.ext_port = ntohs(*(uint16_t *)l_cur);
         }
         l_cur += sizeof(uint16_t);
-        if (a_result) {
-           a_result->hdr.address.uint64 = be64toh(*(uint64_t *)l_cur);
+        if (l_dns_client->result) {
+           l_dns_client->result->hdr.address.uint64 = be64toh(*(uint64_t *)l_cur);
         }
     }
-    closesocket(l_sock);
+
+    l_dns_client->callback_success(a_esocket->worker,l_dns_client->result,l_dns_client->callbacks_arg);
+    l_dns_client->is_callbacks_called = true;
+    a_esocket->flags |= DAP_SOCK_SIGNAL_CLOSE;
 }
 
 /**
@@ -152,11 +153,13 @@ static bool s_dns_client_esocket_timeout_callback(void * a_arg)
  */
 static void s_dns_client_esocket_delete_callback(dap_events_socket_t * a_esocket, void * a_arg)
 {
+    (void) a_arg;
     struct dns_client * l_dns_client = (struct dns_client*) a_esocket->_inheritor;
     if(! l_dns_client->is_callbacks_called )
         l_dns_client->callback_error(a_esocket->worker,l_dns_client->result,l_dns_client->callbacks_arg,EBUSY);
     if(l_dns_client->name)
         DAP_DELETE(l_dns_client->name);
+    DAP_DEL_Z(l_dns_client->buf);
 }
 
 /**
@@ -180,19 +183,20 @@ void dap_chain_node_info_dns_request(struct in_addr a_addr, uint16_t a_port, cha
     l_dns_client->callbacks_arg = a_callbacks_arg;
     l_dns_client->addr = a_addr;
 
-    const size_t l_buf_size = 1024;
-    uint8_t l_buf[l_buf_size];
-    dap_dns_buf_t l_dns_request = {};
-    l_dns_request.data = (char *)l_buf;
-    dap_dns_buf_put_uint16(&l_dns_request, rand() % 0xFFFF);    // ID
+    l_dns_client->buf_size = 1024;
+    l_dns_client->buf = DAP_NEW_Z_SIZE(byte_t,l_dns_client->buf_size);
+    l_dns_client->dns_request->data = (char *)l_dns_client->buf;
+    l_dns_client->result = a_result;
+    dap_dns_buf_put_uint16(l_dns_client->dns_request, rand() % 0xFFFF);    // ID
     dap_dns_message_flags_t l_flags = {};
-    dap_dns_buf_put_uint16(&l_dns_request, l_flags.val);
-    dap_dns_buf_put_uint16(&l_dns_request, 1);                  // we have only 1 question
-    dap_dns_buf_put_uint16(&l_dns_request, 0);
-    dap_dns_buf_put_uint16(&l_dns_request, 0);
-    dap_dns_buf_put_uint16(&l_dns_request, 0);
+    dap_dns_buf_put_uint16(l_dns_client->dns_request, l_flags.val);
+    dap_dns_buf_put_uint16(l_dns_client->dns_request, 1);                  // we have only 1 question
+    dap_dns_buf_put_uint16(l_dns_client->dns_request, 0);
+    dap_dns_buf_put_uint16(l_dns_client->dns_request, 0);
+    dap_dns_buf_put_uint16(l_dns_client->dns_request, 0);
     size_t l_ptr = 0;
-    uint8_t *l_cur = l_buf + l_dns_request.size;
+
+    uint8_t *l_cur = l_dns_client->buf + l_dns_client->dns_request->size;
     for (size_t i = 0; i <= strlen(a_name); i++)
     {
         if (a_name[i] == '.' || a_name[i] == 0)
@@ -206,9 +210,9 @@ void dap_chain_node_info_dns_request(struct in_addr a_addr, uint16_t a_port, cha
         }
     }
     *l_cur++='\0';
-    l_dns_request.size = l_cur - l_buf;
-    dap_dns_buf_put_uint16(&l_dns_request, DNS_RECORD_TYPE_A);
-    dap_dns_buf_put_uint16(&l_dns_request, DNS_CLASS_TYPE_IN);
+    l_dns_client->dns_request->size = l_cur - l_dns_client->buf;
+    dap_dns_buf_put_uint16(l_dns_client->dns_request, DNS_RECORD_TYPE_A);
+    dap_dns_buf_put_uint16(l_dns_client->dns_request, DNS_CLASS_TYPE_IN);
 
     dap_events_socket_callbacks_t l_esocket_callbacks={0};
 
@@ -221,11 +225,13 @@ void dap_chain_node_info_dns_request(struct in_addr a_addr, uint16_t a_port, cha
     l_esocket->remote_addr.sin_family = AF_INET;
     l_esocket->remote_addr.sin_port = htons(a_port);
     l_esocket->remote_addr.sin_addr = a_addr;
+    l_esocket->_inheritor = l_dns_client;
 
     dap_worker_t * l_worker = dap_events_worker_get_auto();
-    dap_events_socket_write_unsafe(l_esocket,l_dns_request.data, l_dns_request.size );
+    dap_events_socket_write_unsafe(l_esocket,l_dns_client->dns_request->data, l_dns_client->dns_request->size );
     dap_events_socket_assign_on_worker_mt(l_esocket,l_worker);
-    dap_timerfd_start_on_worker(l_worker,10000,s_dns_client_esocket_timeout_callback,l_esocket);
+    dap_timerfd_start_on_worker(l_worker, dap_config_get_item_uint64_default(g_config,"dns_client","request_timeout",10)*1000,
+                                 s_dns_client_esocket_timeout_callback,l_esocket);
 }
 
 
diff --git a/modules/net/include/dap_chain_node_dns_client.h b/modules/net/include/dap_chain_node_dns_client.h
index d80ff8f933c8f5dee3912e8dd29fd57bfbcaa1b7..a7b5316a47031b889f85a0e6bd40f76836b2ddab 100644
--- a/modules/net/include/dap_chain_node_dns_client.h
+++ b/modules/net/include/dap_chain_node_dns_client.h
@@ -29,6 +29,8 @@
 #include "dap_worker.h"
 #include "dap_chain_node.h"
 
+#define DNS_LISTEN_PORT 53      // UDP
+
 typedef struct _dap_dns_buf_t {
     char *data;
     uint32_t size;
diff --git a/modules/net/include/dap_chain_node_dns_server.h b/modules/net/include/dap_chain_node_dns_server.h
index b58c09d47ad900c2486f0429ecf39fbf79fea102..ea72b39cb71a677e93606ed59572a67f75c63107 100644
--- a/modules/net/include/dap_chain_node_dns_server.h
+++ b/modules/net/include/dap_chain_node_dns_server.h
@@ -32,7 +32,6 @@
 #include "dap_chain_node.h"
 #include "uthash.h"
 
-#define DNS_LISTEN_PORT 53      // UDP
 #define DNS_TIME_TO_LIVE 600    // Seconds
 #define DNS_HEADER_SIZE 12
 #define DNS_ANSWER_SIZE 16