首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> C++ >> 關於C++

Keil C51 編譯器對標準 C 的擴展關鍵字與記憶體模型深度解析

     編輯:關於C++

前言

Keil C51 編譯器為 8051 系列單晶片提供了豐富的關鍵字擴展,直接對應硬體架構。理解這些擴展是編寫高效、可靠嵌入式程式的關鍵。本文系統整理 8 大類擴展:儲存類型、儲存模式、變數宣告、資料類型、位操作、SFR、指標與函數屬性。

一、擴展關鍵字總覽 (C51 V4.0,共 19 個)


_at_   _idata_   sfr16   alien   interrupt   small
bdata  large    _task_  _Code   bit         pdata
using  reentrant xdata   compact sbit        data
sfr

二、記憶體區域劃分

1. 程式碼區

  • code:最多 64 KB 程式碼空間 (0000H~FFFFH)

2. 內部資料記憶體 (00H~FFH)

關鍵字位址範圍定址方式說明
data00H~7FH直接定址存取最快,適合常用變數
idata00H~FFH間接定址涵蓋完整內部 RAM
bdata20H~2FH位可定址可進行位元操作

3. 外部資料記憶體

關鍵字範圍用途
xdata0000H~FFFFH (64 KB)大型陣列、緩衝區
pdata單頁 256 BytesCompact 模式預設區域,由 P2 埠決定頁碼

4. 特殊功能暫存器 (SFR, 80H~FFH)

關鍵字定址寬度範例
sfr位元組sfr P0 = 0x80;
sfr16字 (16-bit)sfr16 T2 = 0xCC; // T2L=0xCC, T2H=0xCD
sbit位元sbit EA = 0xAF; // 中斷允許位

替代定義方式:

sbit OV = PSW^2;      // 以 SFR 位元定義
sbit OV = 0xD0^2;     // 以位址定義
bit OV = 0xD2;        // 直接指定位址

三、儲存模式

模式預設變數位置優點缺點適用場景
Small內部 RAM (data)速度最快空間極限 128/256 Bytes小型程式
Compact外部 RAM 一頁 (pdata)空間較大,速度中等需管理頁切換中型程式
Large外部 RAM 完整 64 KB (xdata)空間最大速度最慢大型程式

設定位置:專案選項 → C51 標籤 → Memory Model。

四、儲存類型明確宣告

不依賴模式預設,直接指定變數位置:


data   unsigned char  uart_buf[32];
code   const char     msg[] = "Hello!";
xdata  unsigned long  big_array[10][4][4];
pdata  int            compact_buf[128];
idata  char           indirect_var;

五、擴展資料類型

類型大小範圍/用途
bit1 bit0/1,儲於 20H~2FH
sbit1 bit從 SFR/位址定義的位元
sfr8 bitSFR 位址 0~255
sfr1616 bitSFR 字位址 0~65535

其餘 char, enum, short, int, long, float 與 ANSI C 相同。

六、位元變數與位定址

1. bit 型別限制

  • 可作函數參數、傳回值、區域變數
  • 不可 宣告指標 (bit *ptr 錯誤)
  • 不可 形成陣列 (bit arr[5] 錯誤)
  • 含 #pragma disable 或 using 的函數不可傳回 bit

2. 位定址區 (bdata, 20H~2FH) 應用


int  bdata i;
char bdata arr[3];

sbit bit0  = i^0;      // i 的第 0 位
sbit bit15 = i^15;     // i 的第 15 位
sbit a07   = arr[0]^7; // arr[0] 的第 7 位
sbit a17   = arr[1]^7;

七、指標類型詳解

1. 通用指標 (Generic Pointer, 3 Bytes)


long  *ptr1;        // 指向 long,指標本身依模式儲存
char  xdata *ptr2;  // 指向 char,指標本身放 xdata

結構:[記憶體類型(1B)][高位址(1B)][低位址(1B)]

2. 記憶體專用指標 (Memory-Specific Pointer, 1~2 Bytes)


char data  *str;  // 指向 data 區 char
int  xdata *pow;  // 指向 xdata 區 int

僅儲存位移量,效率更高。

3. 指標轉換規則

  • 專用指標傳給需通用指標的函數 → 自動轉換
  • 未宣告函數原型時,專用指標自動轉為通用指標 → 可能導致錯誤,務必 #include 原型
  • 可強制轉型

八、函數屬性擴展

1. 中斷函數


void serial_ISR() interrupt 4 using 1 { /* ISR 程式碼 */ }

// 定義未使用的中斷入口,產生 RETI
void extern0_ISR() interrupt 0 {}
void timer0_ISR() interrupt 1 {}
void extern1_ISR() interrupt 2 {}
void timer1_ISR() interrupt 3 {}
void serial_ISR()  interrupt 4 {}

2. 暫存器銀行切換

using 1 指定使用第 1 組暫存器銀行 (R0~R7),中斷與主程式使用不同銀行可避免衝突。

3. 函數儲存模式指定


void fast_func(void) small {}   // 區域變數置內部 RAM,加速執行

4. #pragma disable

函數執行期間禁止中斷,適用於關鍵區段。

5. 可重入函數


void func(int param) reentrant;

// 建議搭配
#pragma noaregs

編譯器會建立重入堆疊模擬參數傳遞,解決主程式與中斷共用函數的資料破壞問題。

6. PL/M-51 相容

alien 關鍵字指定 PL/M-51 呼叫慣例。

總結

熟練運用 Keil C51 的記憶體關鍵字、儲存模式、位元操作與函數屬性,能充分發揮 8051 硬體效能,編寫出程式碼緊湊、執行高效的嵌入式應用。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved