1. 前言
本文是AliOS Things提供的一套C語(yǔ)言代碼規(guī)范,適用的對(duì)象為符合C99標(biāo)準(zhǔn)的C語(yǔ)言工程。
2. 命名
本節(jié)內(nèi)容均為建議,不作強(qiáng)制要求。
2.1. 總則
各種命名均使用英文單詞及其縮寫(xiě),非特殊情況不能使用漢語(yǔ)拼音或其他語(yǔ)言。
2.2. 文件命名
文件名全部使用小寫(xiě)字母,用_連接。源文件使用.c后綴。頭文件使用.h后綴。
2.3. 類(lèi)型命名
2.3.1. 簡(jiǎn)單類(lèi)型命名
使用typedef自定義的簡(jiǎn)單類(lèi)型命名全部使用小寫(xiě)字母,用_連接,以_t結(jié)尾。例如:
typedefint32_taos_status_t;
2.3.2. 結(jié)構(gòu)體和聯(lián)合體命名
結(jié)構(gòu)體和聯(lián)合體類(lèi)型命名全部使用小寫(xiě)字母,用_連接。建議使用typedef定義一個(gè)整體的名字,以_t結(jié)尾。例如:
typedefstructaos_list_node{ structaos_list_node*prev; structaos_list_node*next; }aos_list_node_t; staticaos_list_node_tlist_node;
2.3.3. 枚舉命名
枚舉類(lèi)型命名全部使用小寫(xiě)字母,用_連接。建議使用typedef定義一個(gè)整體的名字,以_t結(jié)尾。枚舉值命名全部使用大寫(xiě)字母,用_連接,包含表示類(lèi)型的前綴。例如:
typedefenumaos_socket_stage{ AOS_SOCK_STG_DISCONNECTED, AOS_SOCK_STG_CONNECTED, }aos_socket_stage_t; staticaos_socket_stage_tsock_stage=AOS_SOCK_STG_DISCONNECTED;
2.4. 變量命名
變量命名全部使用小寫(xiě)字母,用_連接。數(shù)組名稱(chēng)盡量使用復(fù)數(shù)名詞。例如:
cfg_file_tcfg_files[NUM_CFG_FILES];
表示數(shù)目的變量名稱(chēng)使用num(number的縮寫(xiě))加復(fù)數(shù)名詞。例如:
unsignedintnum_files;
表示序號(hào)的變量名稱(chēng)使用單數(shù)名詞加num或index或idx(index的縮寫(xiě))。例如:
unsignedintfile_num; unsignedintfile_index;
2.5. 函數(shù)命名
函數(shù)命名全部使用小寫(xiě)字母,用_連接。
2.6. 宏命名
一般的宏命名全部使用大寫(xiě)字母,用_連接。例如:
#defineAOS_STRING_MAX_LEN127
模擬函數(shù)使用方式的宏的命名規(guī)則與函數(shù)相同。例如:
#defineaos_dev_set_id(dev,x) do{ (dev)->id=(x); }while(0)
2.7. 前綴
為防止命名空間污染,公用組件中的非static函數(shù)、非static全局變量、全局類(lèi)型、全局宏的命名應(yīng)帶有前綴。例如(假設(shè)前綴為aos):
voidaos_cfg_file_close(intfd); externchar**aos_process_argv; typedefstructaos_list_nodeaos_list_node_t; #defineAOS_STRING_MAX_LEN127
3. 格式
3.1. 文本格式
源文件、頭文件、Makefile等文本文件一律采用UTF-8 without BOM編碼,采用Unix風(fēng)格換行格式。文本文件末尾應(yīng)有且只有一個(gè)換行符,即末尾應(yīng)有且只有一個(gè)空行。
3.2. 行長(zhǎng)度
每行字符數(shù)原則上不超過(guò)120。包含長(zhǎng)路徑的#include語(yǔ)句、頭文件#define保護(hù)可以無(wú)視此規(guī)則。
3.2.1. 表達(dá)式換行
較長(zhǎng)的表達(dá)式可在運(yùn)算符處換行,換行處的運(yùn)算符屬于舊行,新行對(duì)齊到舊行中的相同邏輯層級(jí)。例如:
voidfoo(void) { if((aos_list_next(list_node)!=&list_head&&!priv)|| !(strcmp(symbol,default_symbol)&&blahblahblahblahblahblah()&& meomeomeomeomeomeomeomeomeomeomeomeomeomeomeomeo(NULL))){ /*...*/ } }
3.2.2. 函數(shù)換行
較長(zhǎng)的函數(shù)定義、聲明可在返回值類(lèi)型和函數(shù)名稱(chēng)之間換行。若返回值為指針類(lèi)型,*屬于新行。例如:
staticunsignedlong blahblahblahblahblahblahblahblahblahblahblahblahblahblahblahblahblahblah(void); staticconstmanager_priv_t *blahblahblahblahblahblahblahblahblahblahblahblahblahblahblahblah(intindex);
較長(zhǎng)的函數(shù)定義、聲明、調(diào)用可在參數(shù)列表中間換行,參數(shù)列表中間換行后新行應(yīng)縮進(jìn)至舊行第一個(gè)參數(shù)處。例如:
voidblahblahblahblahblahblahblahblahblah(manager_priv_t*priv,intindex, constchar*proc_name); voidfoo(void) { blahblahblahblahblahblahblahblahblahblah(get_manager_priv(manager),0, "meomeomeomeomeomeomeomeo"); }
3.2.3. 字符串換行
較長(zhǎng)的字符串可在空格處換行,一般情況下?lián)Q行處的空格屬于舊行。例如:
voidfoo(void) { printf("TheGNUoperatingsystemconsistsofGNUpackages" "(programsspecificallyreleasedbytheGNUProject)" "aswellasfreesoftwarereleasedbythirdparties. "); }
3.3. 縮進(jìn)
使用空格縮進(jìn),每次4個(gè)空格。全文不應(yīng)出現(xiàn)制表符(tab)。例如:
voidfoo(unsignedintnbr_processes) { unsignedinti; while(i
宏定義、行尾注釋、結(jié)構(gòu)體、聯(lián)合體、枚舉等內(nèi)部可縮進(jìn)實(shí)現(xiàn)多行對(duì)齊,但不作強(qiáng)制要求。若有縮進(jìn),應(yīng)對(duì)齊到4的整數(shù)倍。例如:
/*此處數(shù)字0縮進(jìn)32個(gè)字符,即位于第33列。*/ #defineSTAGE_UPDATE_CONTINUE0 #defineSTAGE_UPDATE_COMPLETE1 /*合法*/ #defineEVENT_RX_FULL(1U<0) #define?EVENT_TX_EMPTY?(1U?<1) typdef?enum?socket_stage?{ ????/*?此處等號(hào)縮進(jìn)32個(gè)字符,即位于第33列。?*/ ????SOCK_STG_DISCONNECTED???????=?0, ????SOCK_STG_CONNECTED??????????=?1, }?socket_stage_t; /*?此處反斜杠縮進(jìn)40個(gè)字符,即位于第41列。?*/ #define?aos_dev_set_flags(dev,?x)??????? ????do?{???????????????????????????????? ????????(dev)->flags=(x); }while(0) /*合法*/ #defineaos_dev_set_ops(dev,x) do{ (dev)->ops=(x); }while(0) /*此處注釋縮進(jìn)24個(gè)字符,即位于第25列。*/ foo(NULL);/*abc*/ blahblahblahblahblah();/*xyz*/ /*合法*/ foofoofoo();/*abc*/ foofoo();/*xyz*/
分行定義的宏,第二行起應(yīng)縮進(jìn)一次。例如:
#defineaos_dev_set_id(dev,x) do{ (dev)->id=(x); }while(0)
switch塊中的case語(yǔ)句和default語(yǔ)句與switch語(yǔ)句縮進(jìn)層級(jí)相同。例如:
switch(stage){ caseSOCK_STG_DISCONNECTED: foo(); break; caseSOCK_STG_CONNECTED: sock->connected=1; break; default: break; }
3.4. 花括號(hào)
函數(shù)體的左花括號(hào)另起一行;其他情況下左花括號(hào)不另起一行。一般情況下左花括號(hào)后續(xù)內(nèi)容另起一行;宏定義中、數(shù)組、結(jié)構(gòu)體、聯(lián)合體初始化時(shí)若花括號(hào)中內(nèi)容較短則左花括號(hào)后續(xù)內(nèi)容可以不另起一行。一般情況下右花括號(hào)另起一行;宏定義中、數(shù)組、結(jié)構(gòu)體、聯(lián)合體初始化時(shí)若花括號(hào)中內(nèi)容較短則右花括號(hào)可以不另起一行。右花括號(hào)與后續(xù)內(nèi)容組合成一行。例如:
typedefstructmanager_priv{ intindex; void*data; }manager_priv_t; #defineset_manager_index(x,idx)do{(x)->priv->index=(idx);}while(0) #ifdef__cplusplus extern"C"{ #endif voidfoo(void) { inti=0; /*...*/ if(i==0){ /*...*/ }else{ /*...*/ } } manager_priv_tpriv={0,NULL,}; #ifdef__cplusplus } #endif
3.5. 空格
行尾不應(yīng)有空格。三元操作符和二元操作符(獲取成員的.和->操作符除外)前后留有空格。例如:
x=a?b:c; v=w*x+y/z; len=x.length; priv=proc->priv;
一元操作符與參數(shù)之間不留空格。例如:
x=*p; p=&x; i++; j=--i;
逗號(hào)右側(cè)若有內(nèi)容,逗號(hào)與右側(cè)內(nèi)容之間應(yīng)有空格。例如:
voidfoo(intx,inty);
分號(hào)右側(cè)若有內(nèi)容(右圓括號(hào)或另外一個(gè)分號(hào)除外),分號(hào)與右側(cè)內(nèi)容之間應(yīng)有空格。例如:
for(i=0;i
圓括號(hào)內(nèi)部?jī)?nèi)容與圓括號(hào)之間不留空格。例如:
len=strlen(name); for(i=0;i
圓括號(hào)與左側(cè)關(guān)鍵字之間應(yīng)有空格。例如:
while(1){ /*...*/ } if(i==0){ /*...*/ }
圓括號(hào)與左側(cè)函數(shù)名之間不留空格。例如:
intload_file(constchar*name) { foo(0); /*...*/ }
類(lèi)型轉(zhuǎn)換中的圓括號(hào)與右側(cè)內(nèi)容之間不留空格。例如:
manager_priv_t*priv=(manager_priv_t*)p;
方括號(hào)與左側(cè)內(nèi)容、內(nèi)部?jī)?nèi)容之間不留空格。例如:
c=name[i];
左花括號(hào)左側(cè)或右側(cè)若有內(nèi)容,左右內(nèi)容與左花括號(hào)之間應(yīng)有空格。右花括號(hào)左側(cè)若有內(nèi)容,左側(cè)內(nèi)容與右花括號(hào)之間應(yīng)有空格;右花括號(hào)右側(cè)若有內(nèi)容(分號(hào)、逗號(hào)除外),右側(cè)內(nèi)容與右花括號(hào)之間應(yīng)有空格。例如:
#defineset_manager_index(x,idx)do{(x)->priv->index=(idx);}while(0) manager_priv_tpriv={0,NULL,};
分行定義的宏,與左側(cè)內(nèi)容之間應(yīng)有空格。例如:
#defineset_manager_index(x,idx) do{ (x)->priv->index=(idx); }while(0)
3.6. 指針
指針聲明或定義時(shí),*應(yīng)靠近變量名稱(chēng)。*與修飾符之間應(yīng)有空格。例如:
int*p; constchar*name; void*constptr; void(*func)(void*arg);
3.7. 數(shù)值常量
十六進(jìn)制數(shù)字A~F使用大寫(xiě)形式。表示二進(jìn)制的前綴0b和表示十六進(jìn)制的0x使用小寫(xiě)形式。后綴U和L使用大寫(xiě)形式。后綴f使用小寫(xiě)形式。表示冪的e和p使用小寫(xiě)形式。例如:
unsignedintb=0b0101; unsignedintx=0xABCDEF; unsignedintu=0U; longintl=0L; unsignedlongintul=0UL; floatf=1.0f; longdoubleld=1.0L; doubledd=-1.5e-5; doublexd=0xA.Bp12;
3.8. 注釋
使用C90風(fēng)格的/* */,不使用C++風(fēng)格的//。/*或*/與注釋正文之間應(yīng)有空格。行尾的注釋和代碼之間應(yīng)有空格。完整語(yǔ)句注意首字母大寫(xiě)和標(biāo)點(diǎn)符號(hào),簡(jiǎn)單詞組可以不使用標(biāo)點(diǎn)。注意區(qū)分中英文標(biāo)點(diǎn)。TODO:使用特定注釋格式可利用doxygen等自動(dòng)化工具生成文檔。例如:
/* *ThissourcefileispartofAliOSThings. *ZhangSan*2021.07.01 */ /*ZhangSan *2021.07.01*/ /*ThispointermustNOTbeNULL.*/ /*connecting*/
4. 頭文件
4.1. 路徑
為避免與第三方庫(kù)的頭文件命名沖突,公用組件的頭文件應(yīng)存放于子目錄中,引用時(shí)路徑包含子目錄名稱(chēng)。例如:
#include
4.2. 引號(hào)和尖括號(hào)
只有包含與本源文件處于同路徑中的頭文件時(shí)使用引號(hào),其他情況均使用尖括號(hào)。例如:
#include#include"my_demo.h"
4.3. 包含次序
包含頭文件的次序如下:|次序 |種類(lèi)| |-:- |:-| |1 |C語(yǔ)言標(biāo)準(zhǔn)庫(kù)頭文件和工具鏈頭文件| |2 |公用組件的頭文件| |3 |本工程頭文件|
例如:
#include#include #include #include #include"my_demo.h"
4.4. 保護(hù)
所有頭文件都應(yīng)該使用#define保護(hù)來(lái)防止被重復(fù)包含。相關(guān)宏命名格式是PATH_FILE_H。例如,頭文件aos/common.h可按如下方法保護(hù):
#ifndefAOS_COMMON_H #defineAOS_COMMON_H /*全部?jī)?nèi)容*/ #endif/*AOS_COMMON_H*/
4.5. 函數(shù)、變量聲明
頭文件中的函數(shù)聲明不使用extern關(guān)鍵字。頭文件中的全局變量聲明使用extern關(guān)鍵字。例如:
voidaos_cfg_file_close(intfd); externchar**aos_process_argv;
4.6. extern "C"關(guān)鍵字
公用頭文件中聲明的函數(shù)和全局變量應(yīng)該使用extern "C"關(guān)鍵字修飾。#include不應(yīng)使用extern "C"關(guān)鍵字修飾。#define、類(lèi)型定義不作要求,可酌情考慮。例如:
#ifndefAOS_COMMON_H #defineAOS_COMMON_H #include#defineAOS_STRING_MAX_LEN127 #defineAOS_LSTRING_MAX_LEN511 typedefstructaos_tm{ unsignedintsec; unsignedintmin; unsignedinthour; unsignedintmday; unsignedintmon; unsignedintyear; }aos_tm_t; #ifdef__cplusplus extern"C"{ #endif externcharaos_process_symbol[AOS_STRING_MAX_LEN+1]; voidaos_start(void); #ifdef__cplusplus } #endif #endif/*AOS_COMMON_H*/
5. 其他注意事項(xiàng)
只在本編譯單元使用的函數(shù)、全局變量應(yīng)使用static修飾符。在不影響功能的前提下,指針類(lèi)型的函數(shù)參數(shù)盡量使用const修飾符。自增、自減運(yùn)算符單獨(dú)使用時(shí)采用后置形式。數(shù)組、結(jié)構(gòu)體初始化列表、枚舉類(lèi)型定義中的最后一個(gè)成員之后應(yīng)有逗號(hào)。例如:
intoffsets[]={ 0, 1, };
來(lái)源:https://help.aliyun.com/document_detail/311306.html
審核編輯:劉清
-
嵌入式系統(tǒng)
+關(guān)注
關(guān)注
41文章
3593瀏覽量
129518 -
C語(yǔ)言
+關(guān)注
關(guān)注
180文章
7605瀏覽量
136990 -
BOM
+關(guān)注
關(guān)注
5文章
256瀏覽量
40210 -
UTF-8
+關(guān)注
關(guān)注
0文章
13瀏覽量
7861
原文標(biāo)題:嵌入式實(shí)時(shí)操作系統(tǒng) AliOS Things 的編碼風(fēng)格
文章出處:【微信號(hào):工程師進(jìn)階筆記,微信公眾號(hào):工程師進(jìn)階筆記】歡迎添加關(guān)注!文章轉(zhuǎn)載請(qǐng)注明出處。
發(fā)布評(píng)論請(qǐng)先 登錄
相關(guān)推薦
評(píng)論