diff --git a/openair2/RRC/LITE/MESSAGES/asn1_msg.c b/openair2/RRC/LITE/MESSAGES/asn1_msg.c
index e0556b92bfb92dd3ca6a399fef214ff80a7f5a3d..3fe10c92f826c8b81ad2b4f81d723d52e92b131a 100644
--- a/openair2/RRC/LITE/MESSAGES/asn1_msg.c
+++ b/openair2/RRC/LITE/MESSAGES/asn1_msg.c
@@ -117,6 +117,7 @@ typedef struct xer_sprint_string_s {
 } xer_sprint_string_t;
 
 extern unsigned char NB_eNB_INST;
+extern uint8_t usim_test;
 
 uint16_t two_tier_hexagonal_cellIds[7] = {0,1,2,4,5,7,8};
 uint16_t two_tier_hexagonal_adjacent_cellIds[7][6] = {{1,2,4,5,7,8},    // CellId 0
@@ -1268,7 +1269,10 @@ uint8_t do_RRCConnectionSetupComplete(uint8_t Mod_id, uint8_t *buffer, const uin
   rrcConnectionSetupComplete->criticalExtensions.choice.c1.choice.rrcConnectionSetupComplete_r8.nonCriticalExtension=CALLOC(1,
       sizeof(*rrcConnectionSetupComplete->criticalExtensions.choice.c1.choice.rrcConnectionSetupComplete_r8.nonCriticalExtension));
 
-  rrcConnectionSetupComplete->criticalExtensions.choice.c1.choice.rrcConnectionSetupComplete_r8.selectedPLMN_Identity=2;
+  if(usim_test == 0)
+      rrcConnectionSetupComplete->criticalExtensions.choice.c1.choice.rrcConnectionSetupComplete_r8.selectedPLMN_Identity= 2;
+  else
+      rrcConnectionSetupComplete->criticalExtensions.choice.c1.choice.rrcConnectionSetupComplete_r8.selectedPLMN_Identity= 1;
 
   rrcConnectionSetupComplete->criticalExtensions.choice.c1.choice.rrcConnectionSetupComplete_r8.registeredMME =
     NULL;//calloc(1,sizeof(*rrcConnectionSetupComplete->criticalExtensions.choice.c1.choice.rrcConnectionSetupComplete_r8.registeredMME));
diff --git a/openair3/NAS/TOOLS/usim_data.c b/openair3/NAS/TOOLS/usim_data.c
index 1835f0b8b127bbdcf7ab74f778fe52dfdefa5023..126ff4f78c9a9b9c07d3730bb70abf876b8931b7 100644
--- a/openair3/NAS/TOOLS/usim_data.c
+++ b/openair3/NAS/TOOLS/usim_data.c
@@ -227,6 +227,7 @@ int main (int argc, const char* argv[])
     usim_data.imsi.u.num.digit13 = 3;
     usim_data.imsi.u.num.digit14 = 4;
     usim_data.imsi.u.num.digit15 = 0xF;
+    usim_data.usimtestmode = 1; // set usim in test mode in order to get the CMW500 K key
 #endif
     /*
      * Ciphering and Integrity Keys
diff --git a/openair3/NAS/UE/API/USIM/usim_api.c b/openair3/NAS/UE/API/USIM/usim_api.c
index b0ccbf9504ac1c96cfac14898f17c5b71c5d3791..df7d22db8edb31c60b13f9049672c7584a84c30b 100644
--- a/openair3/NAS/UE/API/USIM/usim_api.c
+++ b/openair3/NAS/UE/API/USIM/usim_api.c
@@ -79,6 +79,7 @@ Description Implements the API used by the NAS layer to read/write
 #define USIM_API_K_SIZE         16
 //#define USIM_API_K_VALUE        "fec86ba6eb707ed08905757b1bb44b8f"
 #define USIM_API_K_VALUE        "8BAF473F2F8FD09487CCCBD7097C6862"
+#define TEST_USIM_API_K_VALUE   "000102030405060708090a0b0c0d0e0f" // CMW500 K key
 
 static uint8_t _usim_api_k[USIM_API_K_SIZE];
 
@@ -143,7 +144,14 @@ int usim_api_read(usim_data_t* data)
   }
 
   /* initialize the subscriber authentication security key */
-  _usim_api_hex_string_to_hex_value(_usim_api_k, USIM_API_K_VALUE, USIM_API_K_SIZE);
+  if(data->usimtestmode == 0)
+  {
+    _usim_api_hex_string_to_hex_value(_usim_api_k, USIM_API_K_VALUE, USIM_API_K_SIZE);
+  }
+  else
+  {
+    _usim_api_hex_string_to_hex_value(_usim_api_k, TEST_USIM_API_K_VALUE, USIM_API_K_SIZE);
+  }
 
   free(path);
   LOG_FUNC_RETURN (RETURNok);
@@ -188,6 +196,189 @@ int usim_api_write(const usim_data_t* data)
   LOG_FUNC_RETURN (RETURNok);
 }
 
+/****************************************************************************
+ **                                                                        **
+ ** Name:        usim_api_authenticate_test()                              **
+ **                                                                        **
+ ** Description: Performs mutual authentication of the USIM to the network,**
+ **              checking whether authentication token AUTN can be accep-  **
+ **              ted. If so, returns an authentication response RES and    **
+ **              the ciphering and integrity keys.                         **
+ **              In case of synch failure, returns a re-synchronization    **
+ **              token AUTS.                                               **
+ **                                                                        **
+ **              Key Generation for Test USIM based on 34.108              **
+ **                                                                        **
+ **              Authentication and key generating function algorithms are **
+ **              specified in 3GPP TS 35.206.                              **
+ **                                                                        **
+ ** Inputs:      rand_pP:          Random challenge number                    **
+ **              autn_pP:          Authentication token                       **
+ **                             AUTN = (SQN xor AK) || AMF || MAC          **
+ **                                         48          16     64 bits     **
+ **              Others:        Security key                               **
+ **                                                                        **
+ ** Outputs:     auts_pP:          Re-synchronization token                   **
+ **              res_pP:           Authentication response                    **
+ **              ck_pP:            Ciphering key                              **
+ **              ik_pP             Integrity key                              **
+ **                                                                        **
+ **              Return:        RETURNerror, RETURNok                      **
+ **              Others:        None                                       **
+ **                                                                        **
+ ***************************************************************************/
+int usim_api_authenticate_test(const OctetString* rand_pP, const OctetString* autn_pP,
+                               OctetString* auts_pP, OctetString* res_pP,
+                               OctetString* ck_pP, OctetString* ik_pP)
+{
+  LOG_FUNC_IN;
+
+  int rc;
+  int i;
+
+  LOG_TRACE(INFO, "USIM-API  - rand :%s",dump_octet_string(rand_pP));
+  LOG_TRACE(INFO, "USIM-API  - autn :%s",dump_octet_string(autn_pP));
+
+  //step1: XDOUT = RAND xor K
+  //       RES = XDOUT
+  for (i=0; i<USIM_API_K_SIZE; i++)
+  {
+      res_pP->value[i] = rand_pP->value[i] ^ _usim_api_k[i];
+  }
+
+  //step2: res = f2(xdout,n)
+  //       ck  = f3(xdout)
+  //       ik  = f4(xdout)
+  //       ak  = f5(xdout)
+  u8 ak[USIM_API_AK_SIZE];
+  for (i=0; i<15; i++)
+  {
+      ck_pP->value[i] = res_pP->value[i+1];
+  }
+  ck_pP->value[15] = res_pP->value[0];
+
+  for (i=0; i<14; i++)
+  {
+      ik_pP->value[i] = res_pP->value[i+2];
+  }
+  ik_pP->value[14] = res_pP->value[0];
+  ik_pP->value[15] = res_pP->value[1];
+
+  for (i=0; i<USIM_API_AK_SIZE; i++)
+  {
+      ak[i] = res_pP->value[i+3];
+  }
+  LOG_TRACE(INFO, "USIM-API  - res(f2)  :%s",dump_octet_string(res_pP));
+  LOG_TRACE(INFO, "USIM-API  - ck(f3)   :%s",dump_octet_string(ck_pP));
+  LOG_TRACE(INFO, "USIM-API  - ik(f4)   :%s",dump_octet_string(ik_pP));
+  LOG_TRACE(INFO, "USIM-API  - ak(f5)   : %02X%02X%02X%02X%02X%02X",
+            ak[0],ak[1],ak[2],ak[3],ak[4],ak[5]);
+
+  //step3: concatenate SQN with AMP SQN||AMF
+  //       SQN = AUTN xor ak
+  u8 sqn[USIM_API_SQN_SIZE];
+  for (i = 0; i < USIM_API_SQN_SIZE; i++) {
+    sqn[i] = autn_pP->value[i] ^ ak[i];
+  }
+  LOG_TRACE(INFO, "USIM-API  - Retrieved SQN %02X%02X%02X%02X%02X%02X",
+            sqn[0],sqn[1],sqn[2],sqn[3],sqn[4],sqn[5]);
+  LOG_TRACE(INFO, "USIM-API  - Retrieved AMF %02X%02X",
+            autn_pP->value[USIM_API_SQN_SIZE],autn_pP->value[USIM_API_SQN_SIZE+1]);
+
+#define USIM_API_XMAC_SIZE 8
+  u8 cdout[USIM_API_XMAC_SIZE];
+  for (i = 0; i < USIM_API_XMAC_SIZE; i++)
+  {
+    if(i < USIM_API_SQN_SIZE)
+    {
+        cdout[i] = sqn[i];
+    }
+    else
+    {
+        cdout[i] = autn_pP->value[i];
+    }
+  }
+  LOG_TRACE(INFO, "USIM-API  - Retrieved CDOUT %02X%02X%02X%02X%02X%02X%02X%02X",
+          cdout[0],cdout[1],cdout[2],cdout[3],cdout[4],cdout[5],cdout[6],cdout[7]);
+
+  //step4:calculate XMAC from cdout and xdout
+  u8 xmac[USIM_API_XMAC_SIZE];
+  for(i = 0; i < USIM_API_XMAC_SIZE; i++)
+  {
+      xmac[i] = res_pP->value[i] ^ cdout[i];
+  }
+  LOG_TRACE(INFO,
+            "USIM-API  - Computed XMAC %02X%02X%02X%02X%02X%02X%02X%02X",
+            xmac[0],xmac[1],xmac[2],xmac[3],
+            xmac[4],xmac[5],xmac[6],xmac[7]);
+
+  /* Compare the XMAC with the MAC included in AUTN */
+#define USIM_API_AMF_SIZE 2
+
+  if ( memcmp(xmac, &autn_pP->value[USIM_API_SQN_SIZE + USIM_API_AMF_SIZE],
+              USIM_API_XMAC_SIZE) != 0 ) {
+    LOG_TRACE(INFO,
+              "USIM-API  - Comparing the XMAC with the MAC included in AUTN Failed");
+    rc = RETURNerror;
+    //LOG_FUNC_RETURN (RETURNerror);
+  } else {
+    LOG_TRACE(INFO,
+              "USIM-API  - Comparing the XMAC with the MAC included in AUTN Succeeded");
+    /* Verify that the received sequence number SQN is in the correct range */
+    rc = _usim_api_check_sqn(*(uint32_t*)(sqn), sqn[USIM_API_SQN_SIZE - 1]);
+  }
+
+
+  if (rc != RETURNok) {
+    /* Synchronisation failure; compute the AUTS parameter */
+
+    /* Concealed value of the counter SQNms in the USIM:
+     * Conc(SQNMS) = SQNMS ⊕ f5*K(RAND) */
+    f5star(_usim_api_k, rand_pP->value, ak);
+
+
+    u8 sqn_ms[USIM_API_SQNMS_SIZE];
+    memset(sqn_ms, 0, USIM_API_SQNMS_SIZE);
+
+    //#define USIM_API_SQN_MS_SIZE  3
+    printf("_usim_api_data.sqn_ms %p\n",_usim_api_data.sqn_ms);
+    for (i = 0; i < USIM_API_SQNMS_SIZE; i++) {
+      //#warning "LG:BUG HERE TODO"
+      printf("i %d:  ((uint8_t*)(_usim_api_data.sqn_ms))[USIM_API_SQNMS_SIZE - i] %d\n",i, ((uint8_t*)(_usim_api_data.sqn_ms))[USIM_API_SQNMS_SIZE - i]);
+      sqn_ms[USIM_API_SQNMS_SIZE - i] =
+        ((uint8_t*)(_usim_api_data.sqn_ms))[USIM_API_SQNMS_SIZE - i];
+    }
+
+    u8 sqnms[USIM_API_SQNMS_SIZE];
+
+    for (i = 0; i < USIM_API_SQNMS_SIZE; i++) {
+      sqnms[i] = sqn_ms[i] ^ ak[i];
+    }
+
+    LOG_TRACE(DEBUG, "USIM-API  - SQNms %02X%02X%02X%02X%02X%02X",
+              sqnms[0],sqnms[1],sqnms[2],sqnms[3],sqnms[4],sqnms[5]);
+
+    /* Synchronisation message authentication code:
+     * MACS = f1*K(SQNMS || RAND || AMF) */
+#define USIM_API_MACS_SIZE USIM_API_XMAC_SIZE
+    u8 macs[USIM_API_MACS_SIZE];
+    f1star(_usim_api_k, rand_pP->value, sqn_ms,
+           &rand_pP->value[USIM_API_SQN_SIZE], macs);
+    LOG_TRACE(DEBUG, "USIM-API  - MACS %02X%02X%02X%02X%02X%02X%02X%02X",
+              macs[0],macs[1],macs[2],macs[3],
+              macs[4],macs[5],macs[6],macs[7]);
+
+    /* Synchronisation authentication token:
+     * AUTS = Conc(SQNMS) || MACS */
+    memcpy(&auts_pP->value[0], sqnms, USIM_API_SQNMS_SIZE);
+    memcpy(&auts_pP->value[USIM_API_SQNMS_SIZE], macs, USIM_API_MACS_SIZE);
+    auts_pP->length = USIM_API_SQNMS_SIZE + USIM_API_MACS_SIZE;
+    LOG_FUNC_RETURN (RETURNerror);
+  }
+
+  LOG_FUNC_RETURN (RETURNok);
+}
+
 /****************************************************************************
  **                                                                        **
  ** Name:        usim_api_authenticate()                                   **
diff --git a/openair3/NAS/UE/API/USIM/usim_api.h b/openair3/NAS/UE/API/USIM/usim_api.h
index f7e85f95e7b8df4e013967b3f3ddce0bc74c037d..fd4b3e33013029bd43cd0ed54e0f815eda3ad0f0 100644
--- a/openair3/NAS/UE/API/USIM/usim_api.h
+++ b/openair3/NAS/UE/API/USIM/usim_api.h
@@ -334,6 +334,8 @@ typedef struct {
   usim_epsloci_t epsloci;
   /* Non-Access Stratum configuration       */
   usim_nasconfig_t nasconfig;
+  /* usim test mode */
+  uint8_t usimtestmode;
 } usim_data_t;
 
 /****************************************************************************/
@@ -351,5 +353,8 @@ int usim_api_write(const usim_data_t* data);
 int usim_api_authenticate(const OctetString* rand, const OctetString* autn,
                           OctetString* auts, OctetString* res,
                           OctetString* ck, OctetString* ik);
+int usim_api_authenticate_test(const OctetString* rand, const OctetString* autn,
+                               OctetString* auts, OctetString* res,
+                               OctetString* ck, OctetString* ik);
 
 #endif /* __USIM_API_H__*/
diff --git a/openair3/NAS/UE/EMM/Authentication.c b/openair3/NAS/UE/EMM/Authentication.c
index 6285534450091b69ac51617bac62f6fbaa78ebc8..96f28d7e86b3d9db9ace43273214728a7712bbda 100755
--- a/openair3/NAS/UE/EMM/Authentication.c
+++ b/openair3/NAS/UE/EMM/Authentication.c
@@ -86,6 +86,8 @@ extern void *_emm_service_t3417_handler(void *);
 extern void *_emm_detach_t3421_handler(void *);
 extern void *_emm_tau_t3430_handler(void *);
 
+extern uint8_t usim_test;
+
 /****************************************************************************/
 /*******************  L O C A L    D E F I N I T I O N S  *******************/
 /****************************************************************************/
@@ -240,7 +242,14 @@ int emm_proc_authentication_request(int native_ksi, int ksi,
        * of the core network by means of the received AUTN parameter and
        * request the USIM to compute RES, CK and IK for given RAND
        */
-      rc = usim_api_authenticate(rand, autn, &auts, &res, &ck, &ik);
+      if(usim_test == 0)
+      {
+        rc = usim_api_authenticate(rand, autn, &auts, &res, &ck, &ik);
+      }
+      else
+      {
+        rc = usim_api_authenticate_test(rand, autn, &auts, &res, &ck, &ik); // XOR algo for autentication on usim test mode
+      }
     }
 
     if (rc != RETURNok) {
diff --git a/openair3/NAS/UE/EMM/SAP/EmmDeregisteredNormalService.c b/openair3/NAS/UE/EMM/SAP/EmmDeregisteredNormalService.c
index 25924fd9f27e5971fbf90a7d5be8e9b81e88a653..167c80ee513a37fd3eb58e9e94077f0bb1e306c3 100755
--- a/openair3/NAS/UE/EMM/SAP/EmmDeregisteredNormalService.c
+++ b/openair3/NAS/UE/EMM/SAP/EmmDeregisteredNormalService.c
@@ -62,6 +62,7 @@ Description Implements the EPS Mobility Management procedures executed
 /****************************************************************************/
 /****************  E X T E R N A L    D E F I N I T I O N S  ****************/
 /****************************************************************************/
+extern uint8_t usim_test;
 
 /****************************************************************************/
 /*******************  L O C A L    D E F I N I T I O N S  *******************/
@@ -116,7 +117,14 @@ int EmmDeregisteredNormalService(const emm_reg_t *evt)
     /*
      * Initiate the attach procedure for EPS services
      */
-    rc = emm_proc_attach(EMM_ATTACH_TYPE_EPS);
+    if(usim_test == 0)
+    {
+      rc = emm_proc_attach(EMM_ATTACH_TYPE_EPS);
+    }
+    else
+    {
+      rc = emm_proc_attach(EMM_ATTACH_TYPE_IMSI); // CMW500 IMSI initial attach expected
+    }
     break;
 
   case _EMMREG_ATTACH_REQ:
diff --git a/openair3/NAS/UE/EMM/emm_main.c b/openair3/NAS/UE/EMM/emm_main.c
index dbeacaa149080fedad33093e9cc796bd72348605..3ec9aa5cac86f3bebb9009ad8528d4890849c5b3 100755
--- a/openair3/NAS/UE/EMM/emm_main.c
+++ b/openair3/NAS/UE/EMM/emm_main.c
@@ -59,6 +59,7 @@ Description Defines the EPS Mobility Management procedure call manager,
 /****************************************************************************/
 /****************  E X T E R N A L    D E F I N I T I O N S  ****************/
 /****************************************************************************/
+extern uint8_t usim_test;
 
 /****************************************************************************/
 /*******************  L O C A L    D E F I N I T I O N S  *******************/
@@ -166,6 +167,7 @@ void emm_main_initialize(emm_indication_callback_t cb, const char *imei)
   /*
    * Get USIM application data
    */
+  _usim_data.usimtestmode = usim_test;
   if ( usim_api_read(&_usim_data) != RETURNok ) {
     /* The USIM application may not be present or not valid */
     LOG_TRACE(WARNING, "EMM-MAIN  - Failed to read USIM application data");
diff --git a/targets/RT/USER/lte-softmodem.c b/targets/RT/USER/lte-softmodem.c
index d055eea3adbbfa6907b62af3e2ecdefdd6b223ec..ba4988cbfab3f50385f2a0ddfca83a1a41f83dca 100644
--- a/targets/RT/USER/lte-softmodem.c
+++ b/targets/RT/USER/lte-softmodem.c
@@ -212,6 +212,7 @@ char   rf_config_file[1024];
 
 int chain_offset=0;
 int phy_test = 0;
+uint8_t usim_test = 0;
 
 
 char ref[128] = "internal";
@@ -387,6 +388,7 @@ void help (void) {
   printf("  --loop-memory get softmodem (UE) to loop through memory instead of acquiring from HW\n");
   printf("  --mmapped-dma sets flag for improved EXMIMO UE performance\n");  
   printf("  --single-thread runs lte-softmodem in only one thread\n"); 
+  printf("  --usim-test use XOR autentication algo in case of test usim mode\n"); 
   printf("  -C Set the downlink frequency for all component carriers\n");
   printf("  -d Enable soft scope and L1 and L2 stats (Xforms)\n");
   printf("  -F Calibrate the EXMIMO borad, available files: exmimo2_2arxg.lime exmimo2_2brxg.lime \n");
@@ -693,6 +695,7 @@ static void get_options (int argc, char **argv)
     LONG_OPTION_DUMP_FRAME,
     LONG_OPTION_LOOPMEMORY,
     LONG_OPTION_PHYTEST,
+    LONG_OPTION_USIMTEST,
     LONG_OPTION_MMAPPED_DMA,
     LONG_OPTION_SINGLE_THREAD,
 #if T_TRACER
@@ -719,6 +722,7 @@ static void get_options (int argc, char **argv)
     {"ue-dump-frame", no_argument, NULL, LONG_OPTION_DUMP_FRAME},
     {"loop-memory", required_argument, NULL, LONG_OPTION_LOOPMEMORY},
     {"phy-test", no_argument, NULL, LONG_OPTION_PHYTEST},
+    {"usim-test", no_argument, NULL, LONG_OPTION_USIMTEST},
     {"mmapped-dma", no_argument, NULL, LONG_OPTION_MMAPPED_DMA},
     {"single-thread", no_argument, NULL, LONG_OPTION_SINGLE_THREAD},
 #if T_TRACER
@@ -818,6 +822,9 @@ static void get_options (int argc, char **argv)
       phy_test = 1;
       break;
 
+    case LONG_OPTION_USIMTEST:
+        usim_test = 1;
+      break;
     case LONG_OPTION_MMAPPED_DMA:
       mmapped_dma = 1;
       break;