@@ -49,7 +49,7 @@ extern void make_labelfile(char* xfilename, char* labelfilename) {
4949 lblbuf * nadrs ;
5050
5151 if ((fp = fopen (labelfilename , "w" )) == NULL ) {
52- err ("\n %s をオープンできません。\n" , labelfilename );
52+ err ("%s をオープンできません。\n" , labelfilename );
5353 }
5454
5555 make_header (fp , xfilename );
@@ -108,23 +108,34 @@ typedef enum {
108108} LabelFilePass ;
109109
110110static char * skipspace (char * ptr ) {
111- while (* ptr == ' ' || * ptr == '\t' ) ptr ++ ;
111+ while (isblank ( * ptr )) ptr += 1 ;
112112 return ptr ;
113113}
114114
115115static char * untilspace (char * ptr ) {
116- while (* ptr && * ptr != ' ' && * ptr != '\t' ) ptr ++ ;
116+ while (* ptr && ! isblank ( * ptr )) ptr += 1 ;
117117 return ptr ;
118118}
119119
120+ static inline char upper (char c ) { return toupper (c ); }
121+
122+ static int error (const char * filename , int line , const char * msg ) {
123+ eprintf ("%s:%d: %s\n" , filename , line , msg );
124+ return 1 ;
125+ }
126+
120127// データ系の属性文字列を変換する
121- static boolean parseLabelAttrD (char * * pStr , lblmode * pAttr ) {
128+ static int parseLabelAttrD (const char * filename , int line , const char * * pStr ,
129+ lblmode * pAttr ) {
122130 lblmode attr = DATLABEL ;
123- char * p = * pStr ;
131+ const char * p = * pStr ;
132+
133+ if (* p == '\0' )
134+ return error (filename , line , "属性Dにはサイズの指定が必要です。" );
124135
125- switch (toupper (* p ++ )) {
136+ switch (upper (* p ++ )) {
126137 default :
127- return FALSE ;
138+ return error ( filename , line , "属性Dのサイズが不正です。" ) ;
128139
129140 case 'B' :
130141 attr |= BYTESIZE ;
@@ -160,9 +171,11 @@ static boolean parseLabelAttrD(char** pStr, lblmode* pAttr) {
160171 attr |= UNKNOWN ;
161172 break ;
162173
174+ // 過去のバージョンでは相対オフセットテーブルをDR、DRL
175+ // と規定していたので、互換性のために残す
163176 case 'R' :
164177 attr |= RELTABLE ;
165- if (toupper (* p ) == 'L' ) {
178+ if (upper (* p ) == 'L' ) {
166179 p += 1 ;
167180 attr ^= (RELTABLE ^ RELLONGTABLE );
168181 }
@@ -171,81 +184,85 @@ static boolean parseLabelAttrD(char** pStr, lblmode* pAttr) {
171184
172185 * pStr = p ;
173186 * pAttr = attr ;
174- return TRUE ;
187+ return 0 ;
175188}
176189
177190// 属性文字列をopesizeに変換する
178- // 成功時はattrptrに書き込んでTRUEを返す
179- static boolean parseLabelAttribute (char * p , lblmode * attrptr ) {
180- lblmode attr = DATLABEL ;
181- char c = * p ++ ;
191+ static int parseLabelAttribute (const char * filename , int line , const char * p ,
192+ lblmode * pAttr ) {
193+ * pAttr = DATLABEL ;
194+
195+ if (* p == '\0' ) return error (filename , line , "属性が指定されていません。" );
182196
183- switch (toupper ( c )) {
197+ switch (upper ( * p ++ )) {
184198 default :
185- return FALSE ;
199+ return error ( filename , line , "不正な属性です。" ) ;
186200
187201 case 'P' :
188- attr = PROLABEL ;
202+ * pAttr = PROLABEL ;
189203 break ;
190204
191205 case 'R' :
192- c = * p ++ ;
193- switch (toupper (c )) {
206+ switch (upper (* p ++ )) {
194207 default :
195- return FALSE ;
208+ return error ( filename , line , "属性Rにはサイズの指定が必要です。" ) ;
196209 case 'W' :
197- attr |= RELTABLE ;
210+ * pAttr |= RELTABLE ;
198211 break ;
199212 case 'L' :
200- attr |= RELLONGTABLE ;
213+ * pAttr |= RELLONGTABLE ;
201214 break ;
202215 }
203216 break ;
204217
205- case 'D' :
206- if (!parseLabelAttrD (& p , & attr )) return FALSE;
207- break ;
218+ case 'D' : {
219+ int e = parseLabelAttrD (filename , line , & p , pAttr );
220+ if (e ) return e ;
221+ } break ;
208222 }
209223
210- while (1 ) {
211- c = toupper (* p );
212- if (c == 'F' ) {
213- p += 1 ;
214- attr |= FORCE ;
215- } else if (c == 'H' ) {
216- p += 1 ;
217- attr |= HIDDEN ;
218- } else {
219- break ;
224+ // 追加の属性 f, h
225+ while (* p && !isblank (* p )) {
226+ switch (upper (* p ++ )) {
227+ default :
228+ return error (filename , line , "不正な追加の属性です。" );
229+
230+ case 'F' :
231+ * pAttr |= FORCE ;
232+ break ;
233+ case 'H' :
234+ * pAttr |= HIDDEN ;
235+ break ;
220236 }
221237 }
222238
223- * attrptr = attr ;
224- return TRUE;
239+ return 0 ;
225240}
226241
227- // ラベルファイルの1行を解析する
228- static int get_line ( char * linebuf , int line , address * adrs , char * * symptrptr ,
229- boolean * isLower , const char * filename ) {
230- address ad = ( address ) atox ( linebuf ) ;
231- char * ptr = skipspace ( untilspace ( linebuf )) ;
232- lblmode attr = 0 ;
242+ typedef struct {
243+ address adrs ;
244+ lblmode attr ;
245+ boolean isLower ;
246+ char * symptr ;
247+ } LabelLine ;
233248
234- * isLower = islower (* ptr ) ? TRUE : FALSE;
249+ // ラベルファイルの1行を解析する
250+ static int get_line (const char * filename , int line , char * linebuf ,
251+ LabelLine * lblline ) {
252+ char * atr = skipspace (untilspace (linebuf ));
235253
236- if (!parseLabelAttribute (ptr , & attr )) {
237- err ("\n%s:%d: " PRI_ADRS ": 不正な文字です。" , filename , line , ad );
238- }
254+ lblline -> adrs = (address )atox (linebuf );
255+ lblline -> attr = PROLABEL ;
256+ lblline -> isLower = islower (* atr ) ? TRUE : FALSE;
257+ lblline -> symptr = skipspace (untilspace (atr ));
239258
240- * symptrptr = skipspace (untilspace (ptr ));
241- * adrs = ad ;
242- return attr ;
259+ return parseLabelAttribute (filename , line , atr , & lblline -> attr );
243260}
244261
245262static void regLabel (address adrs , lblmode attr , int line ,
246263 const char * filename ) {
247264 if (!regist_label (adrs , attr ))
248- eprintf ("\n %s:%d: " PRI_ADRS " ???. " , filename , line , adrs );
265+ eprintf ("%s:%d: " PRI_ADRS " ???.\n " , filename , line , adrs );
249266}
250267
251268// 相対オフセットテーブルの解析を呼び出す
@@ -266,7 +283,7 @@ static void workLower(address adrs, lblmode attr, int line,
266283
267284 if (isPROLABEL (attr )) {
268285 if (!analyze (adrs , ANALYZE_IGNOREFAULT )) {
269- eprintf ("\n %s:%d: " PRI_ADRS "からはプログラムと見なせません。" , filename ,
286+ eprintf ("%s:%d: " PRI_ADRS "からはプログラムと見なせません。\n " , filename ,
270287 line , adrs );
271288 }
272289 return ;
@@ -315,35 +332,36 @@ static void addSymbols(char* s, address adrs) {
315332
316333static void parseLabelFile (FILE * fp , const char * filename , LabelFilePass pass ) {
317334 int line ;
335+ int errorCount = 0 ;
318336
319337 for (line = 1 ;; line ++ ) {
320338 char linebuf [1024 ];
321- char * symptr ;
322- address adrs ;
323- lblmode attr ;
324- boolean isLower ;
339+ LabelLine lblline ;
325340
326341 if (fgets (linebuf , sizeof (linebuf ), fp ) == NULL ) break ;
327342 removeTailLf (linebuf );
328343 if (!isxdigit (linebuf [0 ])) continue ;
329344
330- attr = get_line (linebuf , line , & adrs , & symptr , & isLower , filename );
345+ errorCount + = get_line (filename , line , linebuf , & lblline );
331346
332347 if (pass == PASS_UPPER_FIRST ) {
333348 // 最初のパスで大文字小文字に関わらずラベルとシンボルを登録する
334- regLabel (adrs , attr , line , filename );
335- addSymbols (symptr , adrs );
349+ regLabel (lblline . adrs , lblline . attr , line , filename );
350+ addSymbols (lblline . symptr , lblline . adrs );
336351 } else {
337- if (isLower ) workLower (adrs , attr , line , filename );
352+ if (lblline .isLower )
353+ workLower (lblline .adrs , lblline .attr , line , filename );
338354 }
339355 }
356+
357+ if (errorCount ) err ("ラベルファイルに%d個のエラーがあります。\n" , errorCount );
340358}
341359
342360// ラベルファイルを読み込む
343361void read_labelfile (char * filename ) {
344362 FILE * fp = fopen (filename , "rt" );
345363
346- if (fp == NULL ) err ("\n %s をオープンできません。\n" , filename );
364+ if (fp == NULL ) err ("%s をオープンできません。\n" , filename );
347365
348366 parseLabelFile (fp , filename , PASS_UPPER_FIRST );
349367 rewind (fp );
0 commit comments