<?xml version="1.0" encoding="UTF-8" ?>
<?xml-stylesheet type="text/xsl" href="https://devzone.nordicsemi.com/cfs-file/__key/system/syndication/rss.xsl" media="screen"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Runtime restart advertising with new MAC and services</title><link>https://devzone.nordicsemi.com/f/nordic-q-a/40983/runtime-restart-advertising-with-new-mac-and-services</link><description>Hi 
 I have a requirement to be able to re-start advertising with new parameters when told to do so over a Slave SPI interface. From other posts, it appears that there is no way to &amp;#39;de-init&amp;#39; the soft-device - eg to remove and re-add services. Rather,</description><dc:language>en-US</dc:language><generator>Telligent Community 13</generator><lastBuildDate>Wed, 05 Dec 2018 12:33:26 GMT</lastBuildDate><atom:link rel="self" type="application/rss+xml" href="https://devzone.nordicsemi.com/f/nordic-q-a/40983/runtime-restart-advertising-with-new-mac-and-services" /><item><title>RE: Runtime restart advertising with new MAC and services</title><link>https://devzone.nordicsemi.com/thread/160370?ContentTypeID=1</link><pubDate>Wed, 05 Dec 2018 12:33:26 GMT</pubDate><guid isPermaLink="false">137ad170-7792-4731-bb38-c0d22fbe4515:28af3c22-2f27-465d-8c48-b4593ec52de5</guid><dc:creator>veletron</dc:creator><description>&lt;p&gt;Hi&lt;/p&gt;
&lt;p&gt;I got this working in the end, mostly by tracking the current state of the comms: idle, advertising, advertising-paired, connected etc, and doing whats necessary:&lt;/p&gt;
&lt;p&gt;&lt;pre class="ui-code" data-mode="c_cpp"&gt;void StartAdvertising(uint8_t bAllowedApps)
{
		MurataStatus_e eMurataStatus = GS_GetMurataStatus();
		if (eMurataStatus != eMurataStatus_Idle &amp;amp;&amp;amp; eMurataStatus != eMurataStatus_BleDisabled)
		{
				NRF_LOG_INFO(&amp;quot;Can&amp;#39;t Advertise While MurataStatus: %s &amp;quot;,GS_GetTexturalMurataStatus(eMurataStatus));
				return;
		}
	
		GC_SetAllowedApps(bAllowedApps);
		GC_SetRandomMacAddr();
	    GC_SetRandomTestConUuid();
			
		//To reset the SD you need to disable it, and then re-enable it...
		if (GS_GetMurataStatus() != eMurataStatus_BleDisabled)
				ble_stack_teardown();
		
		ble_stack_init();
		gap_params_init();
		services_init();
		advertising_init();
	    conn_params_init();
        ConfigureTagForPatientAppNfcPairing(bAllowedApps);
		AdvertiseOnDisconnect(true);
		advertising_start(true);
	
}


void ProcessTheIncommingMessage(p_str_ProteusMsgWithPayload_t psIncommingProteusMessage)
{
		if (!MessageSrcIsValid(&amp;amp;psIncommingProteusMessage-&amp;gt;sProteusMsg) || !MessageDstIsValid(&amp;amp;psIncommingProteusMessage-&amp;gt;sProteusMsg))
		{
				//todo NAK the message
				return;
		}
	
	
		if(!MessageIsForMe(&amp;amp;psIncommingProteusMessage-&amp;gt;sProteusMsg))
		{
				AddMessageToQueue(psIncommingProteusMessage);
				return;
		}
				
		//If we get here then this Message is for the Murata, so process it...
			
			
		//We will need the current Murata status in the calls below
		MurataStatus_e eCurrentMurataStatus = GS_GetMurataStatus();
		NRF_LOG_INFO(&amp;quot;Recieved Command: %s&amp;quot;,GetTexuralBleMcuCommand((BleMcuCommand_e)psIncommingProteusMessage-&amp;gt;sProteusMsg.bCommandId));
		
		switch ((BleMcuCommand_e)psIncommingProteusMessage-&amp;gt;sProteusMsg.bCommandId)
		{
				case eBleMcuCommand_GlobalSetup:      				//Passes the struct: BleMcu_GlobalSetup_t
					
						if (!TestMurataStatus(eCurrentMurataStatus,eMurataStatus_Idle,true))
								break;
				
						//So a size test on the expected length of the payload data - just ignore if not valid
						if (psIncommingProteusMessage-&amp;gt;sProteusMsg.wPayloadSize == sizeof(str_BleMcu_GlobalSetup_t))
								DoGlobalSetup((p_str_BleMcu_GlobalSetup_t)psIncommingProteusMessage-&amp;gt;psPayloadBuffer-&amp;gt;PayloadBuffer);
							
						break;
					
				case eBleMcuCommand_Disconnect:
											
						if (!TestMurataStatus(eCurrentMurataStatus,eMurataStatus_Connected,true))
								break;
						
						AdvertiseOnDisconnect(false);
						ble_disconnect();
						break;

				case eBleMcuCommand_StopAdvertising:

						if (!TestMurataStatus(eCurrentMurataStatus,eMurataStatus_Advertising,true))
								break;
																					
						advertising_stop();
						break;
						
						
				case eBleMcuCommand_StartAdvertising:
					
						if (!TestMurataStatus(eCurrentMurataStatus,eMurataStatus_Idle,true))
								break;
						
						if (!GC_AreMacAddrAndTestConIdValid())
						{
								NRF_LOG_INFO(&amp;quot;ERROR: MAC and/or TestConId not yet set&amp;quot;);
								break;
						}
						
						AdvertiseOnDisconnect(true);
						advertising_start(false);
						break;
										
				case eBleMcuCommand_BleOnAllApps:            //Sets the Murata System Settings struct. Allows the connection of any Mobile App (starts advertising)
					
					StartAdvertising(eAllowedApps_PatientApp | eAllowedApps_TechnicianApp | eAllowedApps_ProductionApp);
					break;
				
				case eBleMcuCommand_BleOnPatientTechApp:     //Sets the Murata System Settings struct. Allows the connection Patient and Tech Apps (starts advertising)
					
					StartAdvertising(eAllowedApps_PatientApp | eAllowedApps_TechnicianApp);
					break;
	
				case eBleMcuCommand_BleOnPatientApp:         //Sets the Murata System Settings struct. Allows the connection Patient App Only (starts advertising)
					
					StartAdvertising(eAllowedApps_PatientApp);
					break;
	
				case eBleMcuCommand_BleOnTechApp:         //Sets the Murata System Settings struct. Allows the connection Tech App Only (starts advertising)
					
					StartAdvertising(eAllowedApps_TechnicianApp);
					break;
	
				case eBleMcuCommand_BleOff:         //Tells any connected App that BLE is turning off, Disconnects App and turns off BLE. If no connected App, stops advertising, turns BLE off
					
					if (TestMurataStatus(eCurrentMurataStatus,eMurataStatus_Connected,false))
					{
							//todo - send message to app to tell it we are disconnecting from it
							AdvertiseOnDisconnect(false);
							ble_disconnect();
					}
					
					if (TestMurataStatus(eCurrentMurataStatus,eMurataStatus_Advertising,false))
							advertising_stop();
										
					if (WaitForStatus(eMurataStatus_Idle,100))
							eCurrentMurataStatus = GS_GetMurataStatus();
					else
							break;
					
					DeleteNfcTagData();
					ble_stack_teardown();   //Tear down the BLE stack - one of the start advertising commands will restart it
					//delete_bonds();       //&amp;lt;-- Dont do this here as deleting the bonds restarts advertising via a callback - instead, bond will be deleted when we re-start BLE and call advertising_start(true)
					GC_InvalidateMacAddrAndTestConId();
										
					break;
					
				case eBleMcuCommand_GetCurrentState:         //Murata will respond by sending the current state to the Src endpoint identified by the protocol (using a separate command)
					
					NRF_LOG_INFO(&amp;quot;Murata State: %s&amp;quot;,GS_GetTexturalMurataStatus(eCurrentMurataStatus));
					//todo - implement response
					break;
	
				case eBleMcuCommand_GetFwVersion:            //Requests that the Murata sends its FW Version
				
					//Todo - implement
					break;
	
				case eBleMcuCommand_CacheFile:               //Requests that the Murata Caches the data that will be sent in the payload associated with this command
					
					//todo implement
					break;
	
				case eBleMcuCommand_AccelerometerPacket:     //For Production App only - format is in 
					
					//Todo - implement
					break;
					
				default:
				
					//Not expecting this message - ignore
					break;
		}
		
		//If there was a payload associated with the data we just processed then we need to &amp;#39;free&amp;#39; it
		if (psIncommingProteusMessage-&amp;gt;sProteusMsg.wPayloadSize &amp;gt; 0)
				FreePayloadBuffer(psIncommingProteusMessage-&amp;gt;psPayloadBuffer);
				
}

void ble_stack_teardown(void)
{
		ret_code_t err_code;
	
		if (!nrf_sdh_is_enabled())
				return;

    err_code = nrf_sdh_disable_request();
    APP_ERROR_CHECK(err_code);
	
		//Wait until soft device reports &amp;#39;disabled&amp;#39; state.
		while (nrf_sdh_is_enabled()) 
		{
		    //todo - wrap with timer
		}
		
			
		GS_SetMurataStatus(eMurataStatus_BleDisabled);
	
}
&lt;/pre&gt;&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;</description></item><item><title>RE: Runtime restart advertising with new MAC and services</title><link>https://devzone.nordicsemi.com/thread/159753?ContentTypeID=1</link><pubDate>Fri, 30 Nov 2018 15:29:10 GMT</pubDate><guid isPermaLink="false">137ad170-7792-4731-bb38-c0d22fbe4515:eda5b5ed-3385-4f1d-bcef-607e60a2ced0</guid><dc:creator>Jared</dc:creator><description>&lt;div&gt;&lt;span&gt;Hi&lt;/span&gt;&lt;/div&gt;
&lt;div&gt;&lt;span&gt;&lt;/span&gt;&lt;/div&gt;
&lt;div&gt;&lt;span style="font-family:Arial, Helvetica, sans-serif;"&gt;&lt;span&gt;You are correct in calling a&amp;nbsp;&lt;/span&gt;&lt;/span&gt; &lt;span&gt;&lt;span&gt;&lt;span style="color:#11171a;font-family:&amp;#39;GT Eesti&amp;#39;, Helvetica, Arial, sans-serif;"&gt;nrf_sdh_disable_request() before you disable the softdevice. The correct way of de initializing&amp;nbsp;the softdevice is shown in &lt;a href="https://www.nordicsemi.com/en/DocLib/Content/SDK_Doc/nRF5_SDK/v15-2-0/lib_softdevice_handler?1100#lib_sdh_example_delay_msc"&gt;this chart&lt;/a&gt;.&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/div&gt;
&lt;div&gt;&amp;nbsp;&lt;/div&gt;
[quote user="veletron"]Unfortunately, its now dying elsewhere when I attempt to restart advertising ble_advertising.c line 667[/quote]
&lt;p&gt;&amp;nbsp;How are you restarting the advertising? Are you calling&amp;nbsp;StartAdvertising()? What is the error code that is thrown?&amp;nbsp;&lt;/p&gt;
&lt;p&gt;Jared&amp;nbsp;&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;</description></item><item><title>RE: Runtime restart advertising with new MAC and services</title><link>https://devzone.nordicsemi.com/thread/159400?ContentTypeID=1</link><pubDate>Wed, 28 Nov 2018 11:53:24 GMT</pubDate><guid isPermaLink="false">137ad170-7792-4731-bb38-c0d22fbe4515:abdaf92e-e4d3-41c7-bcb9-fffe731f9c8f</guid><dc:creator>veletron</dc:creator><description>&lt;p&gt;I appear to have managed to get past that but by calling the following to shutdown the SD:&lt;/p&gt;
&lt;p&gt;void ble_stack_teardown(void)&lt;br /&gt;{&lt;br /&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp;ret_code_t err_code;&lt;br /&gt; &lt;br /&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp;if (!nrf_sdh_is_enabled())&lt;br /&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; return;&lt;/p&gt;
&lt;p&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp;err_code = nrf_sdh_disable_request();&lt;br /&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp;APP_ERROR_CHECK(err_code);&lt;br /&gt; &lt;br /&gt;&amp;nbsp; &amp;nbsp; //Wait until soft device reports &amp;#39;disabled&amp;#39; state.&amp;nbsp;&lt;br /&gt;&amp;nbsp; &amp;nbsp; while (nrf_sdh_is_enabled()) {}&lt;br /&gt;}&lt;/p&gt;
&lt;p&gt;&lt;/p&gt;
&lt;p&gt;Unfortunately, its now dying elsewhere when I attempt to restart advertising ble_advertising.c line 667&lt;/p&gt;
&lt;p&gt;&lt;br /&gt; if (p_advertising-&amp;gt;evt_handler != NULL)&lt;br /&gt; {&lt;br /&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp;p_advertising-&amp;gt;evt_handler(p_advertising-&amp;gt;adv_evt);&lt;br /&gt; }&lt;/p&gt;
&lt;p&gt;I assume that this is because the advertising module has been re-initialised - I don&amp;#39;t find a teardown function for this module, but it looks to me that this is what is required.&lt;/p&gt;
&lt;p&gt;Nigel&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;</description></item><item><title>RE: Runtime restart advertising with new MAC and services</title><link>https://devzone.nordicsemi.com/thread/159392?ContentTypeID=1</link><pubDate>Wed, 28 Nov 2018 11:01:07 GMT</pubDate><guid isPermaLink="false">137ad170-7792-4731-bb38-c0d22fbe4515:ff01ee9a-138f-4730-9b90-d25118165d9d</guid><dc:creator>veletron</dc:creator><description>&lt;p&gt;NB: When the above is called the 1st time it works just fine. I then call sd_ble_gap_adv_stop(m_advertising.adv_handle); via another SPI command, then I call the above again. When called the second time (eg when SD is active) it crashes with the&amp;nbsp;&amp;nbsp;NRF_ERROR_INVALID_STATE&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;</description></item></channel></rss>