會員登陸
帳號:

密碼:

記住我



忘記密碼?

現在註冊!
網站導航
最新下載
訪問統計 (自2012/5/3)


正在流覽:   1 名訪客





關於C語言,區域變數的值異常被改變,請大家進來給點意見
高級會員
註冊日期:
2014/12/02 11:55
所屬群組:
註冊會員
文章: 74
等級: 7; EXP: 53
HP : 0 / 163
MP : 24 / 1225
離線
最近寫code的時候碰到關於區域變數的奇怪問題,請大家給點意見
程式碼意思大約如下


BYTE oldCmd
= 0; //Global variable

void CommandExecute(BYTE cmd_t)
{
  
BYTE newCmd_t;
  
  
EA = 0;

  
newCmd_t = cmd_t;
  
  if(
newCmd_t != oldCmd)
  {
    
HalFlashErase(60);
  }

  
oldCmd = newCmd_t;

  
EA = 1;
}

void HalFlashErase(UINT8 pg)
{
  while (
FCTL & 0x80);
  
FADDRH = pg * (HAL_FLASH_PAGE_SIZE / HAL_FLASH_WORD_SIZE / 256);
  
FCTL |= 0x01;
  
asm("NOP");
  while (
FCTL & 0x80);
  
asm("NOP");
}


在這段程式運作期間總中斷是關閉的,所以沒有中斷的干擾
在進入HalFlashErase()後,跳回來CommandExecute()的時候,newCmd_t的值被改變了

請問,newCmd_t的生命週期不是在CommandExecute()結束的時候才會結束嗎,為何newCmd_t的值會被異常改變

是否是因為newCmd_t被編譯器放進了快速暫存區(編譯器為了快速存取在使用),而相同的快速暫存區在跳進HalFlashErase()執行的時候也會被使用到,導致跳出來的時候newCmd_t的值才被改變了

請問各位建議newCmd_t這個變數,是否要宣告成static(讓其永遠存在,這樣就不會被分配進暫存區),或是volatile(不要被最佳化,也別放進暫存區內)

我之前在寫code的時候發現,某次編譯,下面的這種程式碼也出了問題

BYTE i
;
for(
i = 0;i < 60;i++)
  
HalFlashErase(i);

這種程式碼也會有問題,HalFlashErase()並沒有真正的進去我所想要的次數....


現在發生了這個問題想知道原因,要改變寫程式錯誤的觀念...

2月16日 10:33:01
轉換PDF檔 列印


Re: 關於C語言,區域變數的值異常被改變,請大家進來給點意見
資深會員
註冊日期:
2009/10/13 22:29
來自 Taiwan
所屬群組:
註冊會員
文章: 162
等級: 11; EXP: 78
HP : 0 / 269
MP : 54 / 6068
離線
若編譯時不選用最佳化,也會產生這些問題嗎?

2月16日 11:21:32
轉換PDF檔 列印


Re: 關於C語言,區域變數的值異常被改變,請大家進來給點意見
高級會員
註冊日期:
2014/12/02 11:55
所屬群組:
註冊會員
文章: 74
等級: 7; EXP: 53
HP : 0 / 163
MP : 24 / 1225
離線
引用:

nospam 寫道:
若編譯時不選用最佳化,也會產生這些問題嗎?


沒試過,因為當初有問題的程式已被改掉,目前模擬不出來Orz

但是確定是進入副程式後再跳回來的時候值被改掉的,
當初用debug模式下使用單步執行才發現的,
希望有經驗的前輩能指點指點,不然以後使用區域變數的時候若是跳進某副程式再跳回來感覺都怕怕的....而volatile又不能亂用..

2月16日 11:29:56
轉換PDF檔 列印


Re: 關於C語言,區域變數的值異常被改變,請大家進來給點意見
中級會員
註冊日期:
2013/05/26 14:10
來自 台中市潭子區
所屬群組:
註冊會員
文章: 50
等級: 5; EXP: 90
HP : 0 / 122
MP : 16 / 1464
離線
FADDRH = pg * (HAL_FLASH_PAGE_SIZE / HAL_FLASH_WORD_SIZE / 256);

很有可能這行程式出了問題
變數定義太小,或(HAL_FLASH_PAGE_SIZE / HAL_FLASH_WORD_SIZE / 256)出現0/N的狀況

取消括符
FADDRH = pg * HAL_FLASH_PAGE_SIZE / HAL_FLASH_WORD_SIZE / 256 ;

把他分開來DEBUG 就容易多了
FADDRH = pg * HAL_FLASH_PAGE_SIZE ;
FADDRH /= HAL_FLASH_WORD_SIZE ;
FADDRH /= 256 ;

試試看

2月22日 08:01:20
轉換PDF檔 列印


Re: 關於C語言,區域變數的值異常被改變,請大家進來給點意見
高級會員
註冊日期:
2014/12/02 11:55
所屬群組:
註冊會員
文章: 74
等級: 7; EXP: 53
HP : 0 / 163
MP : 24 / 1225
離線
引用:

LoverTech 寫道:
FADDRH = pg * (HAL_FLASH_PAGE_SIZE / HAL_FLASH_WORD_SIZE / 256);

很有可能這行程式出了問題
變數定義太小,或(HAL_FLASH_PAGE_SIZE / HAL_FLASH_WORD_SIZE / 256)出現0/N的狀況

取消括符
FADDRH = pg * HAL_FLASH_PAGE_SIZE / HAL_FLASH_WORD_SIZE / 256 ;

把他分開來DEBUG 就容易多了
FADDRH = pg * HAL_FLASH_PAGE_SIZE ;
FADDRH /= HAL_FLASH_WORD_SIZE ;
FADDRH /= 256 ;

試試看


FADDRH = pg * (HAL_FLASH_PAGE_SIZE / HAL_FLASH_WORD_SIZE / 256);
我也懷疑過這行異常,結果我把code改為以下
FADDRH = pg << 1;

但是區域變數的值還是一樣異常被改變Orz
最後發現到是R6暫存器的值不知為何也變成FADDRH的值了
但是去看HalFlashErase(),被編出來的組合語言,完全沒有使用到R6暫存器,目前只能推斷是Flash Controler有Bug而異常...

2月22日 09:12:42
轉換PDF檔 列印


Re: 關於C語言,區域變數的值異常被改變,請大家進來給點意見
資深會員
註冊日期:
2007/06/05 21:45
所屬群組:
註冊會員
文章: 924
等級: 27; EXP: 8
HP : 0 / 652
MP : 308 / 19171
離線
>> ...請大家進來給點意見

1. 什麼環境?
R6是什麼MCU,什麼compiler...

2. 錯誤?
如何驗證有錯誤(值被改了?)
驗證錯誤(做同樣的事,再度產生錯誤現象)

2月22日 22:26:16
_________________
程式是
依照寫出來(的code),跑出結果
不是依照你想出來的,得到結果

先有需求規格 後有解決方案
轉換PDF檔 列印






無法在此發表文章
可以在此觀看文章
無法回覆文章
無法編輯自己的文章
無法刪除自己的文章
無法發起投票調查
無法在此投票
無法上傳附加檔案
無法不經審核直接發表文章

[進階搜尋]


搜尋
線上教學影片
網頁捷徑
2017 Summer Elite 報名
教育訓練
其它網站連結
電話: 02-25000405
產品技術問題產品技術支援專線:0800-717718 台北02-25088600 新竹03-5778366 Ext. 8600 高雄07-2137830 MicrochipDIRECT 專線: 07-2137830
Powered by XOOPS © 2001-2012 The XOOPS Project