色哟哟视频在线观看-色哟哟视频在线-色哟哟欧美15最新在线-色哟哟免费在线观看-国产l精品国产亚洲区在线观看-国产l精品国产亚洲区久久

0
  • 聊天消息
  • 系統(tǒng)消息
  • 評(píng)論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫(xiě)文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識(shí)你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

通過(guò)篡改特定代碼數(shù)據(jù)修復(fù)單片機(jī)BUG的方法

MCU開(kāi)發(fā)加油站 ? 來(lái)源:嵌入式基地 ? 2023-05-11 09:22 ? 次閱讀
一、前言

嵌入式產(chǎn)品開(kāi)發(fā)中,難以避免地會(huì)因?yàn)楦鞣N原因?qū)е伦詈蟪鲐浀漠a(chǎn)品存在各種各樣的BUG,通常會(huì)給產(chǎn)品進(jìn)行固件升級(jí)來(lái)解決問(wèn)題。記得之前在公司維護(hù)一款BLE產(chǎn)品的時(shí)候,由于前期平臺(tái)預(yù)研不足,OTA參數(shù)設(shè)置不當(dāng),導(dǎo)致少數(shù)產(chǎn)品出現(xiàn)不能OTA的情況,經(jīng)過(guò)分析只需改變代碼中的某個(gè)參數(shù)數(shù)值即可,但是產(chǎn)品在用戶手里,OTA是唯一能更新代碼的方式,只能給用戶重發(fā)產(chǎn)品。后來(lái)在想,是否可以提前做好一個(gè)接口,支持動(dòng)態(tài)地傳輸少量代碼到產(chǎn)品中臨時(shí)運(yùn)行,通過(guò)修改特定位置的Flash代碼數(shù)據(jù)來(lái)修復(fù)產(chǎn)品的棘手BUG?多留一個(gè)后門(mén),有時(shí)候令產(chǎn)品出棘手問(wèn)題的往往是那么一兩行代碼或者幾個(gè)初始化的參數(shù)不對(duì),那么這種方法也可以應(yīng)應(yīng)急,雖然操作比較騷。

二、創(chuàng)建演示工程

本文以STM32F103C8T6單片機(jī)為例創(chuàng)建演示工程,分為app和bootloader兩個(gè)工程。即將mcu的Flash分為“app”和“bootloader”兩個(gè)區(qū)域, bootloader放在0x8000000為起始的24KB區(qū)域內(nèi),app放在0x8006000為起始的后續(xù)區(qū)域。bootloader完成對(duì)app的Flash數(shù)據(jù)修改。

1、app工程

注意app的工程需要在keil上修改ROM起始地址。

c91cdbae-ef1f-11ed-90ce-dac502259ad0.png

還要在app代碼的開(kāi)頭設(shè)置向量偏移(調(diào)用一行代碼):


	

NVIC_SetVectorTable(NVIC_VectTab_FLASH,0x6000);

app工程的邏輯為:先順序執(zhí)行3個(gè)不同速度的LED閃燈過(guò)程(20ms、200ms、500ms、切換亮滅),最后進(jìn)入到一個(gè)循環(huán)狀態(tài)每秒切換一次LED的狀態(tài)閃爍。代碼如下:


	

voidinit_led(void) { GPIO_InitTypeDefGPIO_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE); GPIO_InitStructure.GPIO_Pin=GPIO_Pin_All; GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP; GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz; GPIO_Init(GPIOB,&GPIO_InitStructure); GPIO_ResetBits(GPIOB,GPIO_Pin_10); GPIO_SetBits(GPIOB,GPIO_Pin_10); } voidled_blings_1(void) { uint32_ti; for(i=0;i10;i++) { GPIO_SetBits(GPIOB,GPIO_Pin_10); delay_ms(20); GPIO_ResetBits(GPIOB,GPIO_Pin_10); delay_ms(20); } } voidled_blings_2(void) { uint32_ti; for(i=0;i10;i++) { GPIO_SetBits(GPIOB,GPIO_Pin_10); delay_ms(200); GPIO_ResetBits(GPIOB,GPIO_Pin_10); delay_ms(200); } } voidled_blings_3(void) { uint32_ti; for(i=0;i10;i++) { GPIO_SetBits(GPIOB,GPIO_Pin_10); delay_ms(500); GPIO_ResetBits(GPIOB,GPIO_Pin_10); delay_ms(500); } } intmain() { NVIC_SetVectorTable(NVIC_VectTab_FLASH,0x6000); SysTick_Init(72); init_led(); led_blings_1(); led_blings_2(); led_blings_3(); while(1) { GPIO_SetBits(GPIOB,GPIO_Pin_10); delay_ms(1000); GPIO_ResetBits(GPIOB,GPIO_Pin_10); delay_ms(1000); } }

為了分析匯編和查看bin文件數(shù)據(jù),我們需要在keil中添加兩條命令,分別生成.dis反匯編和.bin的代碼文件。(具體的目錄情況依葫蘆畫(huà)瓢)


	

fromelf--text-a-c--output=all.disObjTemplate.axf fromelf--bin--output=test.binObjTemplate.axf

c9309b76-ef1f-11ed-90ce-dac502259ad0.png

先將app的代碼燒寫(xiě)進(jìn)單片機(jī),注意燒寫(xiě)設(shè)置里面選擇“Erase Sectors”只擦除需要燒寫(xiě)的地方。

2、bootloader工程

在bootloader中分為兩部分,不變的代碼部分和變動(dòng)的代碼部分(error_process函數(shù))。初次編譯的時(shí)候error_process寫(xiě)為空函數(shù),當(dāng)我們有需求對(duì)App進(jìn)行修改的時(shí)候,我們重新編譯工程對(duì)error_process函數(shù)進(jìn)行填充。為了重新編譯工程的時(shí)候不影響之前函數(shù)的鏈接地址,特意將error_process函數(shù)放到代碼區(qū)的最后0x8000800地址處,理由是原來(lái)工程大小是1.51KB,擦除頁(yè)大小是2KB,所以需要2KB對(duì)齊,對(duì)齊處的地址就選擇0x8000800為起始。代碼如下:

	

#defineFLASH_PAGE_SIZE2048 #defineERROR_PROCESS_CODE_ADDR0x8000800 voiderror_process(void)__attribute__((section(".ARM.__at_0x8000800"))); voidinit_led(void) { GPIO_InitTypeDefGPIO_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE); GPIO_InitStructure.GPIO_Pin=GPIO_Pin_All; GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP; GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz; GPIO_Init(GPIOB,&GPIO_InitStructure); GPIO_ResetBits(GPIOB,GPIO_Pin_10); GPIO_SetBits(GPIOB,GPIO_Pin_10); } uint32_tpageBuf[FLASH_PAGE_SIZE/4]; voiderror_process(void) { } voideraseErrorProcessCode(void) { FLASH_Unlock(); FLASH_ClearFlag(FLASH_FLAG_BSY|FLASH_FLAG_EOP| FLASH_FLAG_PGERR|FLASH_FLAG_WRPRTERR); FLASH_ErasePage(ERROR_PROCESS_CODE_ADDR); FLASH_Lock(); } void(*boot_jump2App)(); voidboot_loadApp(uint32_taddr) { uint8_ti; if(((*(vu32*)addr)&0x2FFE0000)==0x20000000) { boot_jump2App=(void(*)())*(vu32*)(addr+4); __set_MSP(*(vu32*)addr); for(i=0;i8;i++) { NVIC->ICER[i]=0xFFFFFFFF; NVIC->ICPR[i]=0xFFFFFFFF; } boot_jump2App(); while(1); } } intmain() { uint32_tflag; SysTick_Init(72); flag=*((uint32_t*)ERROR_PROCESS_CODE_ADDR); if((flag!=0xFFFFFFFF)&&(flag!=0)) { init_led(); GPIO_ResetBits(GPIOB,GPIO_Pin_10); delay_ms(1000); delay_ms(1000); error_process(); eraseErrorProcessCode(); } boot_loadApp(0x8006000); while(1); }

一進(jìn)main函數(shù)就讀取0x8000800地址處的32位數(shù)據(jù),如果不是全F或者全0那么這個(gè)地方是有函數(shù)體存在需要執(zhí)行的,那么將LED亮起2秒鐘代表bootloader識(shí)別到有處理程序需要執(zhí)行(當(dāng)然這里還需要加一些error_process代碼數(shù)據(jù)是否完整之類的判斷機(jī)制,這里演示先略去)。執(zhí)行完處理程序后將處理程序擦除(數(shù)據(jù)變?yōu)槿獸),避免以后每次上電都重復(fù)擦寫(xiě)Flash。

error_process函數(shù)代碼的數(shù)據(jù)由產(chǎn)品正常使用期間通過(guò)數(shù)據(jù)接口傳入直接寫(xiě)入到0x8000800處(這部分的demo略去),編譯后查看生成的bin文件將error_process部分的代碼截取出來(lái)傳輸?shù)紽lash地址0x8000800處。bootloader的代碼燒寫(xiě)進(jìn)單片機(jī)時(shí)注意燒寫(xiě)設(shè)置里面選擇“Erase Sectors”只擦除需要燒寫(xiě)的地方。keil設(shè)置里ROM地址改回0x08000000。 三、修改app的特定參數(shù)

在app的工程中以“l(fā)ed_blings_1”函數(shù)為例,反匯編如下:


	

$t i.led_blings_1 led_blings_1 0x08006558:b510..PUSH{r4,lr} 0x0800655a:2400.$MOVSr4,#0 0x0800655c:e010..B0x8006580;led_blings_1+40 0x0800655e:f44f6180O..aMOVr1,#0x400 0x08006562:4809.HLDRr0,[pc,#36];[0x8006588]=0x40010c00 0x08006564:f7fffea2....BLGPIO_SetBits;0x80062ac 0x08006568:2014.MOVSr0,#0x14 0x0800656a:f7ffffaf....BLdelay_ms;0x80064cc 0x0800656e:f44f6180O..aMOVr1,#0x400 0x08006572:4805.HLDRr0,[pc,#20];[0x8006588]=0x40010c00 0x08006574:f7fffe98....BLGPIO_ResetBits;0x80062a8 0x08006578:2014.MOVSr0,#0x14 0x0800657a:f7ffffa7....BLdelay_ms;0x80064cc 0x0800657e:1c64d.ADDSr4,r4,#1 0x08006580:2c0a.,CMPr4,#0xa 0x08006582:d3ec..BCC0x800655e;led_blings_1+6 0x08006584:bd10..POP{r4,pc} $d 0x08006586:0000..DCW0 0x08006588:40010c00...@DCD1073810432

由于led是20ms交替亮滅一次,如果我們覺(jué)得這個(gè)參數(shù)有問(wèn)題想改成100ms,從匯編上來(lái)說(shuō)就是要改變兩行代碼:

	

0x08006568:2014.MOVSr0,#0x14 0x08006578:2014.MOVSr0,#0x14 改為 0x08006568:20642MOVSr0,#0x64 0x08006578:20642MOVSr0,#0x64

bootloader工程中error_process的函數(shù)實(shí)現(xiàn)如下:


	

voiderror_process(void) { #defineMODIFY_FUNC_ADDR_START0x08006558 uint32_talignPageAddr=MODIFY_FUNC_ADDR_START/FLASH_PAGE_SIZE*FLASH_PAGE_SIZE; uint32_tcnt,i; //1.copyoldcode memcpy(pageBuf,(void*)alignPageAddr,FLASH_PAGE_SIZE); //2.changecode. //由于Flash操作2KB頁(yè)的特性,0x08006558不滿2kb,因此偏移為0x558,0x558/4=342 pageBuf[90+256]=(pageBuf[90+256]&0xFFFF0000)|0x2064; pageBuf[94+256]=(pageBuf[94+256]&0xFFFF0000)|0x2064; //3.eraseoldcode,copynewcode. FLASH_Unlock(); FLASH_ClearFlag(FLASH_FLAG_BSY|FLASH_FLAG_EOP| FLASH_FLAG_PGERR|FLASH_FLAG_WRPRTERR); FLASH_ErasePage(alignPageAddr); cnt=FLASH_PAGE_SIZE/4; for(i=0;i4,pageBuf[i]); } FLASH_Lock(); }

由于Flash的2KB頁(yè)擦除特性,這里先將待修改代碼區(qū)的Flash頁(yè)數(shù)據(jù)拷貝到緩沖buffer里,然后修改buffer里的數(shù)據(jù),之后擦除Flash相關(guān)頁(yè),最后將buffer里修改后的數(shù)據(jù)重新寫(xiě)回到Flash里去。error_process函數(shù)的反匯編如下:


	

$t .ARM.__at_0x8000800 error_process 0x08000800:b570p.PUSH{r4-r6,lr} 0x08000802:4d1a.MLDRr5,[pc,#104];[0x800086c]=0x8006000 0x08000804:142a*.ASRSr2,r5,#16 0x08000806:4629)FMOVr1,r5 0x08000808:4819.HLDRr0,[pc,#100];[0x8000870]=0x20000008 0x0800080a:f7fffcbd....BL__aeabi_memcpy;0x8000188 0x0800080e:4818.HLDRr0,[pc,#96];[0x8000870]=0x20000008 0x08000810:f8d00568..h.LDRr0,[r0,#0x568] 0x08000814:f36f000fo...BFCr0,#0,#16 0x08000818:f2420164B.d.MOVr1,#0x2064 0x0800081c:4408.DADDr0,r0,r1 0x0800081e:4914.ILDRr1,[pc,#80];[0x8000870]=0x20000008 0x08000820:f8c10568..h.STRr0,[r1,#0x568] 0x08000824:4608.FMOVr0,r1 0x08000826:f8d00578..x.LDRr0,[r0,#0x578] 0x0800082a:f36f000fo...BFCr0,#0,#16 0x0800082e:f2420164B.d.MOVr1,#0x2064 0x08000832:4408.DADDr0,r0,r1 0x08000834:490e.ILDRr1,[pc,#56];[0x8000870]=0x20000008 0x08000836:f8c10578..x.STRr0,[r1,#0x578] 0x0800083a:f7fffd53..S.BLFLASH_Unlock;0x80002e4 0x0800083e:20355MOVSr0,#0x35 0x08000840:f7fffcca....BLFLASH_ClearFlag;0x80001d8 0x08000844:4628(FMOVr0,r5 0x08000846:f7fffccd....BLFLASH_ErasePage;0x80001e4 0x0800084a:14ae..ASRSr6,r5,#18 0x0800084c:2400.$MOVSr4,#0 0x0800084e:e007..B0x8000860;error_process+96 0x08000850:4a07.JLDRr2,[pc,#28];[0x8000870]=0x20000008 0x08000852:f8521024R.$.LDRr1,[r2,r4,LSL#2] 0x08000856:eb050084....ADDr0,r5,r4,LSL#2 0x0800085a:f7fffd0d....BLFLASH_ProgramWord;0x8000278 0x0800085e:1c64d.ADDSr4,r4,#1 0x08000860:42b4.BCMPr4,r6 0x08000862:d3f5..BCC0x8000850;error_process+80 0x08000864:f7fffcfe....BLFLASH_Lock;0x8000264 0x08000868:bd70p.POP{r4-r6,pc} $d 0x0800086a:0000..DCW0 0x0800086c:08006000.`..DCD134242304 0x08000870:20000008...DCD536870920

那么這124個(gè)字節(jié)就是最終要傳輸?shù)?x8000800處的函數(shù)數(shù)據(jù)。傳輸完畢后軟復(fù)位mcu,bootloader將app的Flash數(shù)據(jù)進(jìn)行篡改,達(dá)到改變程序功能的目的。

為什么要在bootloader運(yùn)行時(shí)篡改app的數(shù)據(jù)?按理說(shuō)在app運(yùn)行時(shí)接收到error_process函數(shù)的更新數(shù)據(jù)后可以立刻運(yùn)行,但是由于涉及到對(duì)app自身代碼的修改,涉及Flash修改的一些相關(guān)函數(shù)有可能會(huì)被暫時(shí)破壞而導(dǎo)致代碼運(yùn)行崩潰。

四、跳過(guò)app的某些函數(shù)

如果想跳過(guò)“l(fā)ed_blings_1”函數(shù),有2種方法:

1、函數(shù)內(nèi)部跳過(guò)

	
		即將以下匯編語(yǔ)句 0x0800655a:2400.$MOVSr4,#0 修改為 0x0800655a:e013.$B0x08006584

在“l(fā)ed_blings_1”函數(shù)入口處指令修改直接跳轉(zhuǎn)到函數(shù)出口處。至于匯編的機(jī)器碼和用法文末有相關(guān)資料可以查閱。

因?yàn)樾薷奶幍淖止?jié)偏移為0x55a,是pageBuf下標(biāo)為342元素的高2Byte,需要在error_process函數(shù)中做如下修改:


	

pageBuf[342]=(pageBuf[342]&0x0000FFFF)|0xe0130000;

2、函數(shù)調(diào)用處跳過(guò)

main函數(shù)匯編如下:


	

$t i.main main 0x080065f8:f44f41c0O..AMOVr1,#0x6000 0x080065fc:f04f6000O..`MOVr0,#0x8000000 0x08006600:f7fffe5c...BLNVIC_SetVectorTable;0x80062bc 0x08006604:2048HMOVSr0,#0x48 0x08006606:f7ffff01....BLSysTick_Init;0x800640c 0x0800660a:f7ffff85....BLinit_led;0x8006518 0x0800660e:f7ffffa3....BLled_blings_1;0x8006558 0x08006612:f7ffffbb....BLled_blings_2;0x800658c 0x08006616:f7ffffd3....BLled_blings_3;0x80065c0 0x0800661a:e011..B0x8006640;main+72 0x0800661c:f44f6180O..aMOVr1,#0x400 0x08006620:4808.HLDRr0,[pc,#32];[0x8006644]=0x40010c00 0x08006622:f7fffe43..C.BLGPIO_SetBits;0x80062ac 0x08006626:f44f707aO.zpMOVr0,#0x3e8 0x0800662a:f7ffff4f..O.BLdelay_ms;0x80064cc 0x0800662e:f44f6180O..aMOVr1,#0x400 0x08006632:4804.HLDRr0,[pc,#16];[0x8006644]=0x40010c00 0x08006634:f7fffe38..8.BLGPIO_ResetBits;0x80062a8 0x08006638:f44f707aO.zpMOVr0,#0x3e8 0x0800663c:f7ffff46..F.BLdelay_ms;0x80064cc 0x08006640:e7ec..B0x800661c;main+36 $d 0x08006642:0000..DCW0 0x08006644:40010c00...@DCD1073810432

下面是調(diào)用語(yǔ)句


	

0x0800660e:f7ffffa3....BLled_blings_1;0x8006558

直接將此語(yǔ)句改為空語(yǔ)句nop(0xbf00)即可跳過(guò)調(diào)用,由于該命令占用4個(gè)字節(jié),nop是兩個(gè)字節(jié)的命令,所以替換為兩個(gè)nop命令。


	

0x0800660e:bf00bf00....NOP

因?yàn)樾薷奶幍淖止?jié)偏移為0x60e,是pageBuf下標(biāo)為387元素的高2Byte和下標(biāo)為388元素的低2Byte,需要在error_process函數(shù)中做如下修改:


	

pageBuf[387]=(pageBuf[387]&0x0000FFFF)|0xbf000000; pageBuf[388]=(pageBuf[388]&0xFFFF0000)|0x0000bf00;

審核編輯:湯梓紅

聲明:本文內(nèi)容及配圖由入駐作者撰寫(xiě)或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場(chǎng)。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問(wèn)題,請(qǐng)聯(lián)系本站處理。 舉報(bào)投訴
  • 單片機(jī)
    +關(guān)注

    關(guān)注

    6035

    文章

    44553

    瀏覽量

    634766
  • 嵌入式
    +關(guān)注

    關(guān)注

    5082

    文章

    19111

    瀏覽量

    304863
  • STM32
    +關(guān)注

    關(guān)注

    2270

    文章

    10896

    瀏覽量

    355781
  • 代碼
    +關(guān)注

    關(guān)注

    30

    文章

    4780

    瀏覽量

    68539
  • BUG
    BUG
    +關(guān)注

    關(guān)注

    0

    文章

    155

    瀏覽量

    15665

原文標(biāo)題:通過(guò)篡改特定代碼數(shù)據(jù)修復(fù)單片機(jī)BUG的方法

文章出處:【微信號(hào):mcugeek,微信公眾號(hào):MCU開(kāi)發(fā)加油站】歡迎添加關(guān)注!文章轉(zhuǎn)載請(qǐng)注明出處。

收藏 人收藏

    評(píng)論

    相關(guān)推薦

    單片機(jī)bug修復(fù)#單片機(jī)

    單片機(jī)修復(fù)
    笑君愁
    發(fā)布于 :2022年07月21日 20:15:58

    單片機(jī)Bug戰(zhàn)斗的那些經(jīng)歷

    玩轉(zhuǎn)單片機(jī)有幾年的時(shí)間了,從接觸51開(kāi)始就走上了看不到盡頭的程序員之路。也許大多會(huì)認(rèn)為,敲了幾天幾夜代碼將作品或者項(xiàng)目完美完成的那一刻是最開(kāi)心最得意的時(shí)候。我卻認(rèn)為,真正快樂(lè)的是與Bug斗爭(zhēng)的過(guò)程
    發(fā)表于 11-05 17:09

    單片機(jī)Bug戰(zhàn)斗的那些經(jīng)歷

    單片機(jī)有幾年的時(shí)間了,從接觸51開(kāi)始就走上了看不到盡頭的程序員之路。也許大多會(huì)認(rèn)為,敲了幾天幾夜代碼將作品或者項(xiàng)目完美完成的那一刻是最開(kāi)心最得意的時(shí)候。我卻認(rèn)為,真正快樂(lè)的是與Bug斗爭(zhēng)的過(guò)程,最后
    發(fā)表于 12-20 17:15

    單片機(jī)LED段碼數(shù)據(jù)生成器

    電子發(fā)燒友網(wǎng)站提供《單片機(jī)LED段碼數(shù)據(jù)生成器.exe》資料免費(fèi)下載
    發(fā)表于 06-16 23:10 ?20次下載

    LED段碼數(shù)據(jù)生成器

    LED段碼數(shù)據(jù)生成器 單片機(jī)C51常用軟件 簡(jiǎn)單方便。
    發(fā)表于 05-18 14:53 ?10次下載

    單片機(jī)的Bootloader可以實(shí)現(xiàn)用戶輕松升級(jí)程序

    用于更新自身應(yīng)用軟件并獨(dú)立運(yùn)行的代碼,常被用于升級(jí)產(chǎn)品和修復(fù)產(chǎn)品bug。STM8單片機(jī)如果要下載hex文件的話需要通過(guò)
    的頭像 發(fā)表于 10-23 16:57 ?4961次閱讀
    <b class='flag-5'>單片機(jī)</b>的Bootloader可以實(shí)現(xiàn)用戶輕松升級(jí)程序

    STM32 LoRa無(wú)線數(shù)傳模塊 PC通過(guò)串口傳輸數(shù)據(jù)單片機(jī)

    STM32F1單片機(jī),燒錄代碼后,連接LoRa無(wú)線數(shù)傳模塊,在PC上面使用串口助手,通過(guò)串口傳輸數(shù)據(jù)單片機(jī)串口1,并在LCD顯示屏顯示
    發(fā)表于 11-19 11:51 ?79次下載
    STM32 LoRa無(wú)線數(shù)傳模塊 PC<b class='flag-5'>通過(guò)</b>串口傳輸<b class='flag-5'>數(shù)據(jù)</b>到<b class='flag-5'>單片機(jī)</b>

    通過(guò)ESP8266WIFI模塊讓51單片機(jī)向后端交互數(shù)據(jù)

    注意的是在程序燒錄進(jìn)單片機(jī)之前,不能連接RXD和TXD。建議在燒錄代碼之前先用XCOM發(fā)送指令檢驗(yàn)WIFI模塊是否能夠正常使用,不然一直調(diào)試單片機(jī)代碼也是沒(méi)有用的,一下
    發(fā)表于 11-23 16:20 ?14次下載
    <b class='flag-5'>通過(guò)</b>ESP8266WIFI模塊讓51<b class='flag-5'>單片機(jī)</b>向后端交互<b class='flag-5'>數(shù)據(jù)</b>

    新唐單片機(jī)代碼評(píng)審總結(jié)

    昨晚上,我們一個(gè)同事組織了一個(gè)小會(huì)議,大家一起討論了一個(gè)項(xiàng)目的單片機(jī)代碼,這個(gè)單片機(jī)用的是新唐單片機(jī),期間大家也討論了一些問(wèn)題,總結(jié)一下,希望對(duì)寫(xiě)
    發(fā)表于 12-01 16:06 ?15次下載
    新唐<b class='flag-5'>單片機(jī)</b><b class='flag-5'>代碼</b>評(píng)審總結(jié)

    通過(guò)篡改特定代碼數(shù)據(jù)修復(fù)單片機(jī)BUG方法

    分享文章之前,想問(wèn)大家,你們開(kāi)發(fā)的產(chǎn)品如果有bug了,你們回通過(guò)什么什么方式修復(fù)bug
    的頭像 發(fā)表于 03-03 09:15 ?721次閱讀

    基于51單片機(jī)的紅外遙控解碼數(shù)碼管顯示設(shè)計(jì)資料源程序

    基于51單片機(jī)的紅外遙控解碼數(shù)碼管顯示設(shè)計(jì)資料源程序
    發(fā)表于 04-26 15:35 ?5次下載

    基于89C51單片機(jī)的紅外解碼數(shù)碼管顯示源程序

    基于89C51單片機(jī)的紅外解碼數(shù)碼管顯示源程序
    發(fā)表于 05-15 11:07 ?3次下載

    單片機(jī)C代碼嵌套匯編的一些方法

    單片機(jī)C代碼嵌套匯編的一些方法
    的頭像 發(fā)表于 10-18 16:39 ?529次閱讀
    <b class='flag-5'>單片機(jī)</b>C<b class='flag-5'>代碼</b>嵌套匯編的一些<b class='flag-5'>方法</b>

    單片機(jī)解析g代碼方法

    的運(yùn)動(dòng)。 解析G代碼是將其轉(zhuǎn)化為單片機(jī)能夠理解和執(zhí)行的指令集。單片機(jī)解析G代碼方法主要包括以下幾個(gè)方面:G
    的頭像 發(fā)表于 12-22 14:15 ?1762次閱讀

    單片機(jī)代碼自動(dòng)生成器程序

    和輸入/輸出設(shè)備的芯片。它通常用于嵌入式系統(tǒng)中,能夠完成一系列特定的任務(wù)。開(kāi)發(fā)人員編寫(xiě)的單片機(jī)代碼負(fù)責(zé)指導(dǎo)單片機(jī)執(zhí)行相應(yīng)的任務(wù)。然而,編寫(xiě)單片機(jī)
    的頭像 發(fā)表于 01-08 14:12 ?3171次閱讀
    主站蜘蛛池模板: 2022精品福利在线小视频| 亚洲精品色情婷婷在线播放| 国产又爽又黄又不遮挡视频| 一级毛片皇帝 宫女| 你是淫荡的我的女王| 国产AV亚洲一区精午夜麻豆| 亚洲日本欧美国产在线视| 免费观看国产视频| 国产h视频在线观看网站免费| 亚洲精品一二三| 木凡的天空在线收听| 国产传媒在线观看| 中文字幕亚洲第一页| 日韩欧美视频一区二区在线观看 | 伊人激情综合网| 秋霞电影网午夜免费鲁丝片| 国产婷婷一区二区在线观看| 最新国产精品视频免费看| 色迷迷导航| 久久学生精品国产自在拍| 东北疯狂xxxxbbbb中国| 一个人色导航| 日本无修肉动漫在线观看| 精品国产5g影院天天爽| X8X8拨牐拨牐X8免费视频8午夜| 亚洲.日韩.欧美另类| 男同志china免费视频| 国产普通话精品久久| 99re.05久久热最新地址| 午夜福利试看120秒体验区| 麻豆无人区乱码| 国产免费午夜高清| 99riav9 精品香蕉免费大视频| 午夜理伦片免费| 男女无遮挡吃奶gift动态图| 国产睡熟迷奷系列精品| jizzjizz中国大学生| 夜夜国产亚洲视频香蕉| 色戒2小时38分在线观看| 快播苍井空| 国产人妻人伦精品59HHH|