• ベストアンサー

分割ファイルのコンパイルができない

こんにちは。 mikroCというコンパイラを使い、 以下の2つのファイルをコンパイル 使用と思っていますが、 「init12f683が宣言されていない」、という エラーが出てしまいます。 プログラム的に問題あるでしょうか( コンパイラでは、ひとつのプロジェクト を作成し、両方そこに加えてあります)。 ----init12f683.c(自作関数) void init12f683(){ GPIO=0; CMCON0=0b00000111; ANSEL=0b01110000; TRISIO=0b00010000; } ----picc1.c(main) extern void init12f683(void);*宣言はここと、 void main(){ extern void init12f683(void);*ここで両方試しました。 init12f683(); Delay_ms(1000); while(1){ GPIO.F0=1 ; Delay_ms(1000) ; GPIO.F0=0 ; Delay_ms(1000) ; } } externでの関数の宣言は、mainの外に置く場合と、 中に入れる場合、両方試しています。 問題が、プロジェクトファイルの設定にあるのか、 プログラム的におかしいのか(どこがおかしいのか)、 知りたいです。 何か分かる人がいましたら、 よろしくお願いします。

  • rheda
  • お礼率69% (257/372)

質問者が選んだベストアンサー

  • ベストアンサー
  • jppy
  • ベストアンサー率14% (14/99)
回答No.1

コンパイラ(mikroC)の仕様を知らないのですが(すみません調べてません) 下を試してみたらどうでしょう? ----init12f683.c(自作関数) void init12f683(){    ↓ ----init12f683.c(自作関数) void init12f683( void ){ 引数型を「なし」じゃなくて「void型」としてみる的な?

その他の回答 (3)

  • chie65535
  • ベストアンサー率43% (8518/19363)
回答No.4

>----init12f683.c(自作関数) >void init12f683(){ >----picc1.c(main) >extern void init12f683(void);*宣言はここと、 「void init12f683()」と「void init12f683(void)」は「違う型の関数」なので、いくらextern宣言しようが「そんな関数は存在しない」と言われて当たり前。 実体の方の引数が「()」ならexternしている方も「()」に合わせるか、externしている方の引数が「(void)」なら実体の方も「(void)」に合わせよう。

  • gigamac
  • ベストアンサー率57% (8/14)
回答No.3

ちなみに、コンパイル時でしょうか?リンク時でしょうか? リンク時でしたらmain関数があるpicc1.cの中にinit12f683関数をコピペして試してみるのも手ですね(main関数の前にinit12f683関数をコピペです)。 こんな感じです。 【ファイル名:picc1.c】 ------------------- void init12f683(void){ GPIO=0; CMCON0=0b00000111; ANSEL=0b01110000; TRISIO=0b00010000; } void main(void){ init12f683(); Delay_ms(1000); while(1){ GPIO.F0=1 ; Delay_ms(1000) ; GPIO.F0=0 ; Delay_ms(1000) ; } } ------------------- これでエラーがでなければ、リンクに失敗していると思います。

  • S117
  • ベストアンサー率40% (18/45)
回答No.2

エラーメッセージは本当に 「宣言されていない」でしょうか。 とりあえず関数の中に書くのは不適切なので、関数の呼び出しをする関数の前に書いてください。 また、関数のプロトタイプ宣言はデフォルトでexternですので、省略可能です。 で、宣言はちゃんとしているので、定義がないというエラーかもしれません。 プロジェクトファイルでinit12f683.cが対象に含まれているか確認してください。リンク時に失敗しているのかもしれません。 上記は一般的なCコンパイラの場合の対策なので、もしかしたらお持ちのコンパイラに独特の手順が必要かもしれません。そこら辺はマニュアルを読んでもらうか、別の方の回答を期待するしか。 あと、関数の定義で引数を省略していますが、宣言が(void)なので、 void init12f683(void) と、する方がいいでしょう。 また、できればヘッダファイルを使う方がいいでしょう。

関連するQ&A

  • PICのプログラムについて質問です

    使用するPICは16F84Aで、MPLAB IDEv8.88を使ってこのようなプログラムを作りました。 #include"pic.h" static void pic_init(); static void Delay_ms(unsigned char ms); static void Delay_1ms(); void main(){ pic_init(); while(1) { RB0 = 1 ; Delay_ms(250); Delay_ms(250); Delay_ms(250); RB0 = 0 ; Delay_ms(250); Delay_ms(250); Delay_ms(250); } static void pic_init() { // GPIO = 0b00000000; TRISA = 0xFF ; TRISB = 0x00 } static void Delay_ms(unsigned char ms) { unsigned char c; for (c=ms ; c>0 ; c--) { Delay_1ms(); } } static void Delay_1ms() { unsigned int cnt; unsigned int i; cnt = 76; for (i=0 ; i<cnt ; i++) { NOP(); } } ポートB0の出力を0から1にするプログラムなのですが、実行すると Error [314] C:\Users\moriwaki\Desktop\PIC program\step_test2.c; 52.24 ";" expected Error [254] C:\Users\moriwaki\Desktop\PIC program\step_test2.c; 77.0 undefined variable: "pic_init" ********** Build failed! ********** というエラーが出ます。このようなエラーが出る原因を教えて頂けないでしょうか。お願いします。

  • 分割コンパイルについて

    現在分割コンパイルが分からずに苦戦しています。 下記のリストは構造体を使わなければコンパイラを通すことができましたが、 使うとなぜか通りません。 あれこれ試しましたがどうしても分かりません。 何がおかしいのでしょうか? *define.hで全てのファイルへの定義や宣言を行わせています。 ////////////// //Main.cpp ////////////// #include <stdio.h> #include <conio.h> #include "define.h" int main( void ){ Tmp[0].c = 15; printf("a: %d\n", a); printf("b: %d\n", b); printf("c: %d\n", Tmp[0].c); printf("NUM:%d\n", NUM); aaa(); bbb(); getch(); return 0; } ////////////////// // A.cpp ///////////////// #include <stdio.h> #include "define.h" void aaa( void ){ printf("a: %d\n", a); printf("b: %d\n", b); printf("c: %d\n", Tmp[0].c); printf("NUM:%d\n", NUM); } ////////////////// // B.cpp ///////////////// #include <stdio.h> #include "define.h" void bbb( void ){ printf("a: %d\n", a); printf("b: %d\n", b); printf("c: %d\n", Tmp[0].c); printf("NUM:%d\n", NUM); } ////////////////// // define.cpp ///////////////// #include "define.h" int a = 10; int b = 20; struct Parameter { int c; }; struct Parameter Tmp[NUM]; ////////////////// // define.h ///////////////// #define NUM 100 extern int a; extern int b; extern struct Parameter Tmp[NUM]; void aaa( void ); void bbb( void );

  • PIC12F683 のULPW機能につきまして

    PIC12F683の機能のUltra Low-Power Wake-up の機能使おうとこちらhttp://www.picfun.com/pic26.htmlを参考にさせていただいて、GP0に抵抗と、コンデンサをR=200Ω、C=0.1μFで動かしてみました。 取りあえずは動作した(オシロできちんとのこぎりの波形を確認でました)のですが、しばらくすると、GP0がHiの状態のままになってしまいます。 このような現象を経験された方はいないでしょうか? 情報があれば助かります。 この動作を行うためのプログラムは以下のようにしてみました。 (MikroCを使っています) *****************************************************/ #define _ON 1 #define _OFF 0 #define _INPUT 1 #define _OUTPUT 0 #define SIG GPIO.F1 #define PWR GPIO.F5 void interrupt() { // 全体割り込み停止しているので、GPIO.1pin に変化があっても、ここの関数は呼び出されない if (INTCON.GPIF) { INTCON.GPIF = 0; // Port Change Interrupt Flag clear // GPIO.F1 = 1; // delay_ms(700); // 700ms LED ON // GPIO.F1 = 0; } } void opl_sleep() { INTCON.GIE = 0; //全体割り込みは停止 IOC = 0b00000001; // Interrupt pin GP0 only //1pinだけ検知する。 INTCON.GPIF = 0; // Port Change Interrupt Flag clear INTCON.GPIE = 1; //Enables the GPIO port change interrupt //ポート割り込み有効にすればsleepから復帰 TRISIO.F0 = _INPUT; // Input PCON.ULPWUE = _ON; SIG = _OFF; // Low sleep_start: asm{ nop nop nop nop sleep nop nop nop nop } INTCON.GPIE = 0; // disable GPIO port change interrupt INTCON.GPIF = 0; // Port Change Interrupt Flag clear //場合によっては、ここにチャタリング処理(wait)を入れると良い // INTCON.GIE = 1; } void _FloatValToStr( float val, char* str ) { unsigned char ch = 0x00; int val2; val2 = val * 1000; // val2 = val; ch = (val2 / 1000) % 10; // extract 1.0 volts digit str[0] = 48+ch; // write ASCII digit at cursor point str[1] = '.'; ch = (val2 / 100) % 10; // extract 0.1 volts digit str[2] = 48+ch; // write ASCII digit at cursor point ch = (val2 / 10) % 10; // extract 0.01 volts digit str[3] = 48+ch; // write ASCII digit at cursor point ch = val2 % 10; // extract 0.001 volts digit str[4] = 48+ch; // write ASCII digit at cursor point str[5] = 0x00; } void _CheckADC() { short i; double adc; double val = 0; char str[10]; //センサー信号取り込み ( Vref=3.0V : 実測値 ) adc = Adc_Read(2); val = (double)( adc * 300 ) / 1023; val = val / 100; // _FloatValToStr( val, str ); if ( val > 2.5 ) { // センサーに圧が掛かった! PWR = _ON; Delay_ms( 2000 ); PWR = _OFF; } } void main() { unsigned int co; ANSEL = 0b00100; // Configure AN pins as digital // CMCON = 7; // Turn off the comparators OSCCON = 0b01110000; // クロックを8Mhzに設定する。 CMCON0 = 0b00000111; // コンパレータ使用しない PCON = 0b00100000; // Ultra Low-Power Wake-up enabled TRISIO = 0b00000101; //GP0 pin input GPIO = 0; OPTION_REG.NOT_GPPU = 0; //GPIO pull-ups are enabled //内部弱プルアップに設定する WPU = 0b00000001; //PULL-UP REGISTER setting ,only GP0 pull-up SIG = _OFF; while( 1 ) { TRISIO.F0 = _OUTPUT; // Output GPIO.F0 = _ON; // Hi delay_ms(10); /*** for(co=0;co<10;co++){ //500ms だけLEDをピカピカッとやる GPIO.F1 = ~GPIO.F1; delay_ms(50); } **/ opl_sleep(); //SLEEPへ SIG = _ON; _CheckADC(); delay_ms(40); } }

  • 分割コンパイルの初歩

    C言語ですが、.hに実装を書くのは避けたほうが良いといわれます。 私は main.c define.h aaa.h bbb.h みたいなスタイルでコードを書いていました。 まずdefine.hでグローバル変数や、マクロなどの宣言を まとめて行い、ほかの.hやmain.cでも使えるようにして いました。 しかし、以下のような状況のとき、どのように分割すれば 良いのかが分かりません・・・。 たとえば、以下のように、マクロNUM、変数a,bをすべてのファイルで共有して使えるように分割コンパイルするにはどのようにコードを書き直せば良いのでしょうか? //--------------main.c------------------ #include "define.h" #include "aaa.h" #include "bbb.h" int main( void ){   printf("%d", a);   printf("%d", b);   printf("%d", NUM);   aaa();   bbb();   return 0; } //------------define.h------------------ #define NUM 100 int a = 10; int b = 20; void aaa( void ); void bbb( void ); //------------aaa.h------------------ void aaa( void ){   printf("%d", a);   printf("%d", b);   printf("%d", NUM); } //------------bbb.h------------------ void bbb( void ){   printf("%d", a);   printf("%d", b);   printf("%d", NUM); }

  • 分割コンパイルの#defineについて

    分割コンパイルで ファイル1 #include <stdio.h> #define number 10 char string[number]; int main(void){ string[0]='a'; string[1]='b'; file_to(); return 0; } ファイル2 #include <stdio.h> #define number 10 extern char string[number]; void file_to(void){ /***何かの処理をする*****/ } って感じなんですけども、配列string の中身の値をdefineによって指定しているのですが、片方のdefineの値を変更する時、もう一つのdefineも手動で変更しています。関係するファイル数が多くなってくると大変なので、どれかのdefineの値を変化させたら自動的に他のdefineの値も変更するプログラムの組み方はありませんか? 質問がわかりにくいかも知れませんがよろしくお願いします。

  • C言語のコンパイルエラー

    次のようなコードで (宣言等は省略します) extern int main( int argc, char *argv[]) { short ret ; ret = aaa(); } static short aaa() { /* aaa()関数の処理 */ XXXXXXXXX return 1; } というようなコードをコンパイルすると ワーニングで warning: 'aaa' was declared implicitly `extern' and later `static' warning: previous declaration of `aaa' warning: type mismatch with previous implicit declaration というようなメッセージが出ます。 これは、他のソースをまねて作ってるのですが、 参考にしたコードもこのような宣言の仕方になっているのにエラーはでまでん。 何か他にもaaaという関数の定義をしなくてはいけないのでしょうか? どうもstatic宣言とexternのところがよくわかりません。 宜しくお願いします。

  • 分割コンパイル時に構造体....

    レベルの低い質問とは思いますが struct st { int a; int b; }; void a(struct st *ST) { ST->a=1; ST->b=1; } void main() { struct st ST; a(&ST); printf("%d%d",ST.a,ST.b); getch(); } これだと問題なく動作するのですが、ソースファイルを分割して ソース1 void a(struct st *ST); struct st { int a; int b; }; void main() { struct st ST; a(&ST); printf("%d%d",ST.a,ST.b); getch(); } ソース2 void a(struct st *ST) { ST->a=1; ST->b=1; } だとエラーが返ってくるのがなぜなのか解りません ソース2でも同じ構造体の宣言をしなければならないのでしょうか。 長くなり読みにくくなってしまいましたが、よろしくお願いします。

  • JNAでc言語ファイルの読み込み方が分かりません

    JNAでc言語ファイルの読み込み方が分かりません JNAを使用して、javaからcを読み込み動作するプログラムを作っています。 なんとなく定義は分かってきたのですが、 javaのソースコードに CLibrary.INSTANCE.printf(); のように、c言語を書き込んでいる状況なのですが、 JNAを利用した.javaファイルから.cファイルを読み込む方法はありますか? c言語の場合、.cファイルごとに分割された関数をmainが呼び出すとき、 extern void Sample(); とプロトタイプ宣言の後に Sample(); で呼び出せるみたいなので、 これを使って、 CLibrary.INSTANCE.extern void Sample(); とやってみましたが、コンパイルできませんでした;; 他にやり方がありますか? 知ってる方がいらっしゃいましたら、教えてください。 よろしくお願いします。

    • ベストアンサー
    • Java
  • ファイルポインタのヘッダーファイルの配置について

    分割コンパイルをしている別ファイルの別関数から、同じファイルポインタ(main関数でfopen済み)に出力(fprintf)は可能でしょうか? 可能な場合、 1.ファイルポインタをexternで宣言 2.ファイルポインタをヘッダファイル内で宣言 3.その他方法 どの方法で実現できるのでしょうか? サンプルコード等書いていただけたら助かります。 よろしくお願い致します。

  • PICプログラミングに対する質問

    PIC16F627Aを使い、160KHzの周波数を外部に出力したいのですが、うまくいきません。 仕様はこのようになっています。 セラロックとして10MHzを使っています。(20MHzを使うことも考えている) 電源は5Vです。 開発環境はMPLAB IDEに CCS社Cコンパイラを使っています。 現在のプログラムはこのようになっています。 //////////////////////////////////////////////////////////////////////// //タイマ0を用いて160KHzの周波数を出力する //3.1μsでタイマ0の割り込み //////////////////////////////////////////////////////////////////////// #include<16f627a.h> #fuses HS,NOWDT,NOPROTECT,PUT,BROWNOUT,NOLVP  //コンフィグレーションの設定 #use delay(CLOCK = 10000000)      //発振子の周波数10MHz  //delay_ms()の使用 //定数の定義 #byte  PORTA=0x05 #bytePORTB=x06 #byte TMR0 = 0x01 #bit T0IF = 0x0B.2 //タイマ0割り込み処理 #INT_RTCC //タイマ0の割り込み処理関数の宣言 void rtcc_isr(void) { T0IF=0; //タイマ0の割り込みフラグ TMR0=0xF8; //タイマ0の初期値 PORTA^=0x04; //PORTAの出力反転 } //メイン関数 void main(void){ set_tris_a(0xF8); //出力ポートの設定 set_tris_b(0xF7); //出力ポートの設定 setup_timer_0(RTCC_INTERNAL | RTCC_DIV_1);//プリスケーラを使用しない set_timer0(0x0); //TMR0に0x0を書き込む enable_interrupts(INT_RTCC); //タイマ0の割り込み許可 enable_interrupts(GLOBAL); //グローバルの許可 PORTB = 0x7F; //出力 while(1){ //割り込みを待つ delay_ms(1); //1μs } } ///////////////////////////////////////////////////////////////////// このようなプログラムで160KHzの周波数を出力することは可能でしょうか? もし不足の部分や誤っていることがあったら教えてください。

専門家に質問してみよう