• ベストアンサー
※ ChatGPTを利用し、要約された質問です(原文:makeの勉強中なのですが・・・)

makeの勉強中なのですが・・・

このQ&Aのポイント
  • 新米プログラマがmakeの勉強中ですが、いくつかわからない用語があります。
  • makeの学習本で見つけた定義やコマンドが理解できません。
  • 特にサフィックスとldについて詳しく教えてほしいです。

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

  • ベストアンサー
  • K_Senryu
  • ベストアンサー率100% (6/6)
回答No.3

#1 です。 > -cオプションを指定する場合と、 > -cオプションを指定しない場合のldの動きの違いを > 教えてほしいのですが・・・ 動きの違いではなく、-cを指定するとldは動きません。 C言語は、ソースファイルをコンパイルすると中間ファイルになります。 中間ファイルをリンクして、実行可能モジュールが作られます。 流れにすると、 ソースファイル  (xxxx.c)   ↓ コンパイル(cc, gcc) 中間ファイル   (xxxx.o)   ↓ リンク(ld) 実行可能ファイル (xxxx) こんな感じです。 # 本当は、プリプロセスやアセンブルがあるのですが、省略してます。 ご自身でコマンドを打ってみると理解が早いと思いますが、 cc -c program だと、program.o というファイルが出力されます。これが中間ファイルで、 直接実行できません。 cc program.c だと、コンパイルした後にリンクするので、実行可能モジュールが出力されます。 中間ファイルが残っていないのは、リンク後に削除されるからです。 man cc (man gcc)とか man make とかして調べると、もっと細かいことが 載っていますよ。

golvachofu
質問者

お礼

ありがとうございます。 大変参考になりました! ただ、自分の現場だとmakeを実行するのみで makeの内容まで理解しなくても 一応業務はこなせる現場なんです。 ですので、直接業務に関係の無い事柄を 聞くというのも中々はばかられまして・・・ とにかくありがとうございました!

全文を見る
すると、全ての回答が全文表示されます。

その他の回答 (2)

  • K_Senryu
  • ベストアンサー率100% (6/6)
回答No.2

#1 です。 アドバイスというか、おせっかいですが。 新米プログラマなのであれば、こんなところで質問するのではなく、 指導者や先輩に尋ねてみてはいかがでしょうか。 皆さん仕事があふれていて、質問しにくい状況なのでしょうか。 ですが、後輩から質問をされるのは意外とうれしいものだったりします。 周りの人に聞いてみて、嫌がられたので、ここで質問しているのかも しれませんが、それは、その人がその程度の人間だったということです。 何でもかんでも質問されれば、誰でも嫌がるでしょう。しかし、一度 の質問で嫌な顔をするのは、まともな人間ではありませんよね。 文面が冗長で、何を答えればよいのかわかりにくいのですが、ポイント を突いている良い質問であると思います。このような質問は、ぜひ、 先輩に投げかけ、よい人間関係を作るべきでしょう。

全文を見る
すると、全ての回答が全文表示されます。
  • K_Senryu
  • ベストアンサー率100% (6/6)
回答No.1

サフィックスというのは、いわゆる拡張子のことです。 $make program とすると、ターゲットは program になります。 Makefile内に program : から始まる行が無ければ、サフィックスルールに従って program という ファイルを作成します。で、サフィックスルールですが、 .c : $(CC) $(CFLAGS) $(LDFLAGS) $< -o $@ この部分は、 xxxx というファイルは xxxx.c から作れて、その方法は $(CC) $(CFLAGS) $(LDFLAGS) $< -o $@ だよ。という意味になります。 サフィックスルールというぐらいなので、拡張子のみを見て判定します。 結局、program は program.c から作れることが判明し、 $(CC) = cc, $(CFLAGS) = -O, $(LDFLAGS) = であれば、 cc -O program.c -o program となります。 ちなみに、$< は作成元のファイル名、 $@ はターゲットのファイル名を示すマクロです。 なお、サフィックスルールは .c.o: のような形で使うことが多く、この場合は、 xxxx.o は xxxx.c から作れるよ。という意味になります。 あと、ldはリンカのことです。 分割コンパイルをするとよくわかるのですが、簡単な例では、 printf()など多くの標準関数の実体は、libcというライブラリの中に入っています。 program.cの中で、標準関数を呼び出すには、libcとくっつける(リンク) 必要があります。 -c を指定していないので、コンパイル後は自動的にリンクされますよ。 ということです。

golvachofu
質問者

補足

ありがとうございます。 全体の流れについてよくわかりました。 最後に -cオプションを指定する場合と、 -cオプションを指定しない場合のldの動きの違いを 教えてほしいのですが・・・

全文を見る
すると、全ての回答が全文表示されます。

関連するQ&A

  • make実行時のエラーについて

    makeについてお尋ねします(先日、お尋ねした件の延長なのですが)。 あるプログラムソース群からの実行ファイルの作成に関する質問です。 以下操作手順です。 ------------ 1. configure.sh というのが用意されていて、中を見てみたら私の計算機のコンパイラの状況などを調べたりして、make.incを出力しています。それは所定の場所に置かれます。これをマニュアルどおり実行しました。 2. その場所(ソース群とかmakefile,make.incがあるフォルダ)でmakeを実行しました。makeはmakefile, make.incを読み込んでいます。make.incがmakefileから呼ばれている記述も確認しました。 makeを実行すると、makefileの以下の部分がおかしいとしてmakeが終了します。 c.o: $(CC) -c $(CFLAGS) $(INCS) $*.c メッセージとして、 cc -c -I hoge.c cc: fetal error: no input files ----------- $(CC),$(CFLAGS),$(INCS) というのはcc, スペース, -I を意味するようですが、これはどこで指定されるのでしょうか。 make.incの中にはそのようなものを指定するところはありませんでした。Fortranコンパイラは調べて調整されていることが分かり、"FC= gfortran -O3" というような記述が見えます。configure.shを使って調査したことが分かります。 また、cc -c -I abc.c は、-Iでインクルードファイルのフルパスを指定なのでしょうか。man ccによるとそういう風です。 $(INCS)を削除すればいいのかもですが、一応、セットとして導入されているものなので、どこで副作用が出るかわからないのでそのままにしているのですが。理屈が分からないので、自発的に編集することをためらっています。 make全般ですが、どういう分野に属するのでしょうか。C言語の1分野でもなく、必ずしもLinuxの習得の中に組み込まれているわけでもないように見えます。学習するシステムとしてどこに属するのかということですが。その場その場でアドホックに調べて習得していくものなのでしょうか。 if......fiというようにフィーリングではわかるのですが、しっかり説明されるような学習の場面がないのですが。

  • win版インテルコンパイラnmakeについて

    linux版インテルコンパイラ(icc)を使っているmakefileをwindows版インテルコンパイラ(icl)で使えるように書きかえているのですが、コマンドプロンプトでどうもnmakeがうまくいきません。 元のmakefileは、 CC = icc CFLAGS = -O3 -xSSE4.2 CFLAGS2 = $(CFLAGS) -openmp -openmp-report1 LIBS = -lm -liomp5 PROGRAM = foo.exe SRCS = foo1.c foo2.c foo3.c .c.o: $(CC) $(CFLAGS) -c $< .SUFFIXES: .c .o all : $(PROGRAM) $(PROGRAM) : ${OBJS} $(CC) $(CFLAGS) -o $@ ${OBJS} $(LIBS) foo1.o : foo1.c foo.h foo2.o : foo2.c foo.h $(CC) $(CFLAGS2) -c $< foo3.o : foo3.c foo.h clean: rm *.o rm $(PROGRAM) で、書き換えたmakefileは、 CC = icl CFLAGS = -O3 -QxSSE4.2 CFLAGS2 = $(CFLAGS) -Qopenmp # CFLAGS = -W -O3 LIBS = -lm -liomp5 PROGRAM = foo.exe SRCS = foo1.c foo2.c foo3.c .c.o: $(CC) $(CFLAGS) -c $< .SUFFIXES: .c .o all : $(PROGRAM) $(PROGRAM) : ${OBJS} $(CC) $(CFLAGS) -o $@ $(OBJS) $(LIBS) foo1.o : foo1.c foo.h foo2.o : foo2.c foo.h $(CC) $(CFLAGS2) -c $< foo3.o : foo3.c foo.h clean: rm *.o rm $(PROGRAM) です。(投稿の際に見づらかったためスペースや改行はいじってます) CFLAGS2の-openmpを-Qopenmpにしたのと $(PROGRAM)の行の${OBJS}を$(OBJS)にしたぐらいですがエラーが発生します。({}括弧を使っているとエラーが発生したため) エラーメッセージは NMAKE : warning U4006: 特殊マクロは定義されていません : '$<' です。 {}の括弧を()に修正したのも似たエラーが発生したからなのですが、 コマンドプロンプトだと特殊マクロは使えないのでしょうか?

  • h8マイコン GNU環境 プログラムにおけるライブラリ関数の利用

    毎回の質問失礼します。 秋月のH8/3048Fマイコンボードを利用して測定システムの開発を行おうとしています。 現在までGNU環境で、コンパイル、デバッグの開発環境を整えることが出来ました。  現在は測定システムのプログラムとして、まずA/D変換を行うプログラムを作っているところですが、またもや行き詰まってしまいました。 A/D変換を行うプログラムは作成できていますが、実際に動きません。というのも、A/D変換はセンサ等で測定した値を比較電圧と比較し、その比較した値をディジタル値としてADDRレジスタに格納するのと思いますが、ここからその値をLCDに表示させたいというところで出来ずにいます。  その原因はライブラリ関数だと思っています。変換された値を実際の測定したときに戻すときに浮動小数点演算が必要なので、リンクする際にライブラリ関数を組み込まなければいけないと思うのですが、組み込んでも実際にプログラムが動きません。その演算を行うところではなくて、プログラム自体が動かなくなってしまいます。浮動小数点演算を使用しないと、ライブラリ関数を使わないのでプログラムは正常に動きました。 ライブラリ関数の使い方がおかしいのでしょうか。どなたかご存知の方がいらっしゃいましたら回答よろしくおねがいします。 以下にmakefileの内容を載せておきます。 TARGET_FROM = h8300-elf- CC = $(TARGET_FROM)gcc AS = $(TARGET_FROM)gcc LD = $(TARGET_FROM)gcc OBJCOPY = $(TARGET_FROM)objcopy GDB_STUB= true LDSCRIPT = h8_3048f.x CFLAGS = -mh -g #CFLAGS = -mh -O2 -mrelax LDFLAGS = -nostdlib -Wl,-Map,AD_test.map AD_test.abs: h8_3048f.o AD_test.o $(CC) -o AD_test.abs $(CFLAGS) $(LDFLAGS) -T$(LDSCRIPT) h8_3048f.o AD_test.o -lgcc cat AD_test.map h8_3048f.o: h8_3048f.S $(CC) -c $(CFLAGS) h8_3048f.S AD_test.o: AD_test.c $(CC) -c $(CFLAGS) AD_test.c clean: rm AD_test.abs rm AD_test.o rm h8_3048f.o rm AD_test.map

  • 複数のサブディレクトリを一緒にmakeして一つの実行ファイルを作成するには

    いま、Linuxの環境でC言語の勉強しています。 それで、makeを使ってコンパイル方法を調べているのですが、 ソースディレクトリとヘッダーディレクトリを分けて管理している場合に一緒にコンパイルさせる為のMakefileの書き方が分からず困っています。 現在は、同じディレクトリ内にソースファイルとヘッダーファイルが存在してます。ちなみに下記が今のMakefile内容です。 ご存知の方が記述方法もしくは参考サイトを教えて頂けますでしょうか。よろしくお願い致します。 ======================================================== program = test_pro objs = main.o test1.o test2.o CC = gcc CFLAGS = -g -Wall #suffixes_define_rule .SUFFIXES : .c .o $(program) : $(objs) $(CC) $(CFLAGS) -o $@ $^ #suffixes_rule .c.o : $(CC) $(CFLAGS) -c $< .PHONY : clean clean : $(RM) $(objs) #header_depend test1.o : test1.h test2.o : test2.h =====================================================

  • gnu make empty target

    Managing Projects with GNU Make, 3rd Editionを読んでいます。 p.15 Empty targetについてのサンプルでエラーが出ます。 Makefileは以下のとおりです。 ----- prog: size prog.o gcc $(LDFLAGS) -o $@ $^ prog.o: prog.c gcc -c $^ size: prog.o size $^ touch size ----- make prog と実行すると以下のエラーとなります。 ----- gcc -c prog.c size prog.o text data bss dec hex filename 152 0 0 152 98 prog.o touch size gcc -o prog size prog.o size: file not recognized: File truncated make: *** [prog] Error 1 ----- 自分なりの理解では、sizeという空ファイルを作り、そのタイムスタンプをtouchで更新することにより、progをmakeすることができるということだと思います。 ただ、最後に gcc $(LDFLAGS) -o $@ $^ をする時に$^に空ファイルsizeが含まれていて、そのため size: file not recognized: File truncated というエラーを出しているように思います。 そもそものサンプルMakefileが間違っているのでしょうか? あるいはどこかを修正すれば、Empty targetというのが使い物になるのでしょうか?

  • makefile の書き方

    OBJS1 = a.o b.o c.o OBJS2 = d.o e.o f.o OBJS1のそれぞれの元のソースコードと OBJS2のそれぞれに元のソースコードを 違うコンパイルオプションでオブジェクトファイルを作りたいのですが、 間単に書ける方法があれば教えてください。 つまり、以下を簡単に書く方法です。 よろしくお願いします。 a.o: a.c ${CC} ${CFLAGS_1} $< -o $@ b.o: b.c ${CC} ${CFLAGS_1} $< -o $@ c.o: c.c ${CC} ${CFLAGS_1} $< -o $@ d.o: d.c ${CC} ${CFLAGS_2} $< -o $@ e.o: e.c ${CC} ${CFLAGS_2} $< -o $@ f.o: f.c ${CC} ${CFLAGS_2} $< -o $@

  • Makefileと共有ライブラリ

    main.c sub1.c sub2.cに対して 共有ライブラリlibsub1.soとlibsub2.soを生成して それをもちいてmainをコンパイルするMakefileを以下のように記述しました。 CC=gcc LIB= CFLAGS=-Wall TARGET = main SHAD = -shared .SUFFIXES:.so .o SRCS = main.c libsub1.so libsub2.so $(TARGET):$(SRCS) $(CC) -o $@ $(SRCS) @echo "make finished!!" #.o.so: # $(CC) $(SHAD) -o $@ $< libsub1.so:sub1.o gcc -shared -o libsub1.so sub1.o libsub2.so:sub2.o gcc -shared -o libsub2.so sub2.o .c.o: $(CC) -c $< #sub1.o:sub1.c # gcc -c -fPIC sub1.c #sub2.o:sub2.c # gcc -c -fPIC sub2.c clean: @rm -f libsub?.so sub?.o ここで.oから.cを生成するのはサフィックスでできたのですが、同じように.oから.soを生成するのは できませんでした。 #.o.so: # $(CC) $(SHAD) -o $@ $< ここはどのように記述したらいいのでしょうか? 回答お願いします。

  • Linuxのmake時のエラーについて

    あるプログラムをmakeすると下記のメッセージが出たのですが、どうすれば正常にmakeできますでしょうか?他のPCだとできたようです。 よろしくお願い致します。 g++ -L. -lpthread -lrt -lm -o SchedFifoTest SFthread.o SchedFifoTest.o /usr/bin/ld: SchedFifoTest.o: in function `main': SchedFifoTest.cc:(.text.startup+0x5e): undefined reference to `pthread_setaffinity_np' /usr/bin/ld: SFthread.o: in function `ARCS::SFthread::SFthread(unsigned long, void (*)(void*), void*, int)': SFthread.cc:(.text+0x2e9): undefined reference to `pthread_create' /usr/bin/ld: SFthread.cc:(.text+0x336): undefined reference to `pthread_setaffinity_np' /usr/bin/ld: SFthread.o: in function `ARCS::SFthread::~SFthread()': SFthread.cc:(.text+0x36d): undefined reference to `pthread_cancel' collect2: error: ld returned 1 exit status make: *** [Makefile:51: SchedFifoTest] エラー 1

  • 64bitのRedHatでlibSSH2がmakeできません。。

    RedHatEnterprise3で、libsslをmakeすると、 下記のエラーとなり検索しても原因がわからず困っています。 ■libssh2の最新(2-0.14) gcc -o channel.o channel.c -c -g -O2 /usr/include -I/usr/include -Wall -I../include/ -fPIC gcc: -c や -S と一緒に -o を指定すると、複数コンパイルできません make[1]: *** [channel.o] エラー 1 ■libssh2(2-0.13) /usr/bin/ld: /usr/local/lib/libcrypto.a(md5_dgst.o): 再配置 R_X86_64_32 は共有オブジェクトを作成したときには使えません -- -fPIC を付けて再コンパイルしてください /usr/local/lib/libcrypto.a: could not read symbols: 不正な値です collect2: ld はステータス 1 で終了しました Makefileを開き、CFLAGSに-fPICを付けてmakeしましたが 同じエラーメッセージでした(><)どうすれば良いでしょうか? 日本語でGoogleで検索しても見つからないので、 とりあえずコマンドエラーのメッセージだけでも 英語に変える方法だけでも知りたいです。 libsslはRPMもないようで・・手詰まりです。

  • Eclipse 3.5 Galileo + CDT + cygwinで

    Eclipse 3.5 Galileo + CDT + cygwinで、CやC++のプログラムを作りたいと考えています。 しかし、ビルドが通らず、困っています。 行った作業手順は、以下の通りです。 (1)まず、下記サイトを参考に、簡単なCプログラムを作りました。  http://www.c.csce.kyushu-u.ac.jp/~seiichirou/wiki/index.php?Makefile%A4%CE%BD%F1%A4%AD%CA%FD  ----以下、作成したプログラム----  /* hello.c */  #include <stdio.h>  void edajima(void);  int main(int argc, char* argv[]) {   edajima();   return 0;  }  /* edajima.c */  #include <stdio.h>  void edajima(void);  void edajima(void) {   printf("わしが男塾塾長 江田島平八である!!\r\n");  }  ----プログラムここまで---- (2)そして、Makefileを以下のように作成しました。  ----以下、Makefile----  # Makefile  CC = gcc  CXXFLAGS = -O2 -g -Wall -fmessage-length=0  OBJS = edajima.o hello.o  LIBS =  TARGET = hello.exe  $(TARGET): $(OBJS)   $(CC) -o $(TARGET) $(OBJS) $(LIBS)  all: $(TARGET)  hello.o: hello.c   $(CC) -c hello.c  edajima.o: edajima.c   $(CC) -c edajima.c  clean:   rm -f $(OBJS) $(TARGET)  ----Makefileここまで---- (3)次に、EclipseでCのMakefileプロジェクトの作成をしました。   ロケーションは、上記ソースやMakefileがあるディレクトリを指定しました。 (4)Eclipseのプロジェクトエクスプローラで、Makefileを右クリックし、[Makeターゲット]-[作成]   でMakeターゲットを作成しました。 (5)Makefileを右クリックし、[Makeターゲット]-[ビルド]を実行すると、下記エラーが出て、   ビルドに失敗しました。  make hello  gcc -c hello.c  gcc hello.o -o hello  hello.o:hello.c:(.text+0x17): undefined reference to `_edajima'  collect2: ld returned 1 exit status  make: *** [hello] Error 1 どうやら、edajima.cがコンパイルされていない様です。 cygwin上でmakeコマンドを実行すると、ビルドできるので、Makefileは間違っていないと思っているのですが・・・。 どなたか、分かる方、ご教授願います。

このQ&Aのポイント
  • ケーブルTVのインターネット接続サービスに加入し、フレッツ光を解約したい場合、NTTに電話してぷららに問い合わせる必要があります。
  • ぷららの解約手続きについて詳しく教えてほしい場合は、NTTに連絡して問い合わせてください。
  • 【ぷらら】インターネット接続サービスの解約方法について、NTTにお問い合わせいただくか、ぷららの公式ホームページで詳細を確認することができます。
回答を見る