Forum: PC-Programmierung Probleme mit make unter windows


Announcement: there is an English version of this forum on EmbDev.net. Posts you create there will be displayed on Mikrocontroller.net and EmbDev.net.
von Chandler B. (chandler)


Lesenswert?

Hallo,
ich habe ein kleines Projekt (in C unter Windows10), welches ich gerne 
mit make bauen möchte.
Hier komme ich aber nciht weiter
Ordnerstruktur
1
-dokumentation
2
-out
3
-project
4
  -Makefile
5
-src
6
  main.c
7
  main.h
8
  -module
9
    -fun_1
10
      fun_1.c
11
      fun_1.h
1
TARGET = main
2
# Program for comipling C programs
3
CC = gcc
4
5
# Extra flags to give to the compiler
6
# -g    Turn on debug information
7
# -Wall   give verbose compiler warnings
8
# -O0      Compiler otimization (0: do not optimize generated code)
9
# -std=c99  use the C99 standard language definition
10
#  -c    only generate object file ('.o' file)
11
CFLAGS = -g -Wall -O0
12
13
# Extra flags to give to the C poreprocessor
14
CPPFLAGS =
15
16
# Extra flags to give to the linker
17
LDFLAGS =
18
19
# file path
20
PATH_MAIN = ../src
21
PATH_MODULE = $(PATH_MAIN)/module
22
23
# source files
24
SOURCES_MAIN = $(PATH_MAIN)/main.c
25
SOURCES_MODULE = $(PATH_MODULE)/fun_1/fun_1.c
26
27
SOURCES = $(SOURCES_MAIN) $(SOURCES_MODULE)
28
29
BUILD_DIR := ../out
30
OBJECTS = $(SOURCES:.c=.o)
31
  
32
33
$(TARGET) : $(OBJECTS)
34
  $(CC) $(CFLAGS) -o $@ $^ $(LDFLAGS) 
35
36
.PHONY: clean
37
38
clean:
39
  @rm $(OBJECTS)
Wenn ich jetzt im Order "Project" bin und make ausführe (aus dem cmd 
fenster von Windows), wird mir neben jeder C-Sourcefile ein Objekt 
erstellt und im Ordner Project die main.exe

Allerdings wenn ich "make clean" aufrufe, bekomme ich den Fehler
1
process_begin: CreateProcess(NULL, rm ../src/main.o ../src/module/fun_1/fun_1.o, ...) failed.
Dieser Fehler kommt, da "rm" unter windows nicht existiert.
wenn ich "rm" mit "del" ersetze bekomme ich den Fehler
1
Parameterformat nicht ordnungsgemäß - "src".

Wie bekomme ich "make clean" zum laufen? Und wie bekomme ich es, dass 
alle objects und die .exe im Out-Ordner erstellt werden?

von Harald K. (kirnbichler)


Lesenswert?

Chandler B. schrieb:
> wenn ich "rm" mit "del" ersetze bekomme ich den Fehler

Windows verwendet \ als Pfadtrenner, nicht /

von Niklas G. (erlkoenig) Benutzerseite


Lesenswert?

Chandler B. schrieb:
> Wie bekomme ich "make clean" zum laufen?

Am Besten indem du die Unix-Tools inkl "rm" installierst. Da sehr viele 
Makefiles "rm" & Co benutzen, macht es nicht so viel Sinn stattdessen 
"del" zu nutzen.

z.B. in Form von Cygwin, MinGW, GnuWin32, oder auch damit:

https://gnu-mcu-eclipse.github.io/blog/2019/04/22/windows-build-tools-v2-12-20190422-released/

(funktioniert auch ohne Eclipse)

von Monk (roehrmond)


Lesenswert?

Ich habe in dem Verzeichnis, wo das Makefile liegt, eine rm.bat 
erstellt:
1
@echo off
2
REM Provides an rm command under Windows.
3
4
set tmp=%*
5
set tmp=%tmp:/=\%
6
set tmp=%tmp:-f = %
7
8
del /Q %tmp%

Im Makefile rufe ich das so auf:
1
rm -f $(OBJ) $(PRG).hex $(PRG).elf $(PRG).lst $(PRG).map

Windows verwendet dann die rm.bat und Linux den "normalen" rm Befehl. 
Die Batch Datei ersetzt / durch \ und entfernt das -f.

: Bearbeitet durch User
von Bradward B. (Firma: Starfleet) (ltjg_boimler)


Lesenswert?

Es gibt ein Microsofteigens make - "nmake.exe"
https://learn.microsoft.com/de-de/cpp/build/reference/nmake-reference?view=msvc-170

manchmal ist auch die frage ob man die powershell oder cmd.exe benutzt, 
die powershell ist näher an unix.

https://de.wikipedia.org/wiki/PowerShell

"help del" sollte dir eine Kurzanleitung zu del liefern. Und unter dem 
dos-promptwird variablensubstituion nicht mit $ eingeleitet sondern mit 
%, die powershell dagegen sollte auch das $ kennen.

Aber vielleicht solltest du dich erst für eine Shell unter windows 
entscheiden und dir für diese eine Kurzreferenz besorgen.

: Bearbeitet durch User
von Udo K. (udok)


Lesenswert?

Steve van de Grens schrieb:
> Windows verwendet dann die rm.bat und Linux den "normalen" rm Befehl.
> Die Batch Datei ersetzt / durch \ und entfernt das -f.

Windows versteht / anstatt \ .  Eventuell ist es einfacher im makefile 
eine RM variable zu definieren.  MS nmake kann übrigens auch mit 
Leerzeichen besser umgehen.
1
#RM    = rm -f
2
RM    = del
3
4
clean:
5
  $(RM) *.obj *.lst *.exe

: Bearbeitet durch User
von Hannes J. (Firma: _⌨_) (pnuebergang)


Lesenswert?

Udo K. schrieb:
> Windows versteht / anstatt \ .

Windows selber ja, Windows-Programme häufig nicht. Besonders pervers 
ist, dass das zum Beispiel bei del und Konsorten vom verwendeten 
Befehlszeileninterpreter abhängt:

cmd.exe, del versteht / nicht
1
C:\>type nul > %TEMP%\dummy.txt
2
3
C:\>dir %TEMP%\dummy.txt
4
 Datenträger in Laufwerk C: ist xxx
5
 Volumeseriennummer: xxx
6
7
 Verzeichnis von C:\Users\xxx\AppData\Local\Temp
8
9
2024-05-31  23:50                 0 dummy.txt
10
               1 Datei(en),              0 Bytes
11
               0 Verzeichnis(se), 1040.942.960.640 Bytes frei
12
13
C:\>del %TEMP%/dummy.txt
14
Ungültige Option - "dummy.txt".
15
16
C:\>del %TEMP%\dummy.txt

Powershell, del versteht / und \
1
PS C:\> New-Item $Env:temp\dummy.txt
2
3
4
    Verzeichnis: C:\Users\xxx\AppData\Local\Temp
5
6
7
Mode                 LastWriteTime         Length Name
8
----                 -------------         ------ ----
9
-a----        2024-05-31     23:52              0 dummy.txt
10
11
12
PS C:\> del $Env:temp\dummy.txt
13
PS C:\> New-Item $Env:temp\dummy.txt
14
15
16
    Verzeichnis: C:\Users\xxx\AppData\Local\Temp
17
18
19
Mode                 LastWriteTime         Length Name
20
----                 -------------         ------ ----
21
-a----        2024-05-31     23:52              0 dummy.txt
22
23
24
PS C:\> del $Env:temp/dummy.txt

Kurz gesagt, ist halt Windows, ist halt scheiße.

von Udo K. (udok)


Lesenswert?

Hannes J. schrieb:
> Windows selber ja, Windows-Programme häufig nicht. Besonders pervers
> ist, dass das zum Beispiel bei del und Konsorten vom verwendeten
> Befehlszeileninterpreter abhängt:

Ok, interessanterweise hatte ich das Problem nie.  Meine Makefiles sind 
vielleicht zu einfach.

> Kurz gesagt, ist halt Windows, ist halt scheiße.

Das ist mal wieder eine polemische und überflüssige Aussage.  Windows 
ist halt komplex und hat historische Altlasten. Aber Microsoft zahlt 
wenigstens sehr gutes Schmerzensgeld.

Linux ist da nicht besser.  Da gibt es sh, bash, ash, dash, csh, ksh, 
und ein Duzend weitere.  Jede mit eigener Syntax, jede inkompatibel. 
Und sh auf Debian ist nicht kompatibel mit der sh in Ubuntu.  Und das 
gnu rm ist nicht kompatibel mit dem FreeBSD rm.  Ah ja, gmake das meist 
unter dem Name make installiert ist, ist nicht kompatibel zu sysv make.

Wieviel Stunden habe ich mit der Suche nach Fehlern in Shell Skripten 
verbraten? Dann war es das "alias" Kommando, das Befehle auf der 
interaktiven Kommandozeile umdefiniert, oder eine Umgebungsvariable, die 
mal gesetzt war und dann wieder nicht.   Und Schmerzensgeld hat da 
keiner gezahlt.

: Bearbeitet durch User
von Monk (roehrmond)


Lesenswert?

Udo K. schrieb:
> Aber Microsoft zahlt wenigstens sehr gutes Schmerzensgeld.

Ich habe von denen noch keinen Cent erhalten. Im Gegenteil: Ich muss 
seit 25 Jahren meine PC mit OEM Windows kaufen, obwohl ich kein Windows 
haben will. Und ich kann es danach nicht einmal weiter verkaufen, an 
andere die Interesse hätten.

> Und sh auf Debian ist nicht
> kompatibel mit der sh in Ubuntu.

Alternative Fakten?

Alle Linux Versionen nutzen standardmäßig eine Bourne Shell oder eine 
dazu kompatible. Wenn du Erweiterungen spezifischer Shells nutzt, und 
diese dann bei anderen Shells nicht zur Verfügung stehen, dann ist das 
dein eigenes hausgemachtes Problen. Dafür kann weder der Herr Torvalds 
etwas, noch das Linux System.

Dass Leute alternative Shells bereit stellen ist weder ein Problem von 
Linux noch von Windows. Genieße die Freiheit, oder lasse es sein, wenn 
du nicht magst.

: Bearbeitet durch User
von Harald K. (kirnbichler)


Lesenswert?

Steve van de Grens schrieb:
> Im Gegenteil: Ich muss
> seit 25 Jahren meine PC mit OEM Windows kaufen, obwohl ich kein Windows
> haben will.

Aha. Falscher PC-Händler? PCs ohne vorinstallierte Windows gab es schon 
vor 30 Jahren.

Oder kaufst Du ausschließlich Notebooks?

von Monk (roehrmond)


Lesenswert?

Harald K. schrieb:
> PCs ohne vorinstallierte Windows gab es schon vor 30 Jahren.

Ha, aber noch teurer als mit Windows. Das sind diese "bitte kaufen sie 
das nicht" Angebote, die nur existieren, um Microsoft + Händler 
juristisch unangreifbar zu machen.

: Bearbeitet durch User
von Udo K. (udok)


Lesenswert?

Steve van de Grens schrieb:
>> Und sh auf Debian ist nicht
>> kompatibel mit der sh in Ubuntu.
>
> Alternative Fakten?

https://wiki.ubuntu.com/DashAsBinSh
Was glaubst du wie viele Shell Skripte es da aufgehaut hat.

Hier Gehälter von Microsoft - und von da ist es ja nur ein kleiner 
Sprung über den Atlantik, wo die Gehälter noch mal deutlich zulegen:
https://www.kununu.com/de/microsoft-deutschland/gehalt

Und hier beispielhaft die Situation der OSS:
https://is.gd/4sXESA (*)

(*) Die Forensoftware zensuriert Links die nicht ins Konzept passen, 
daher der is.gd Link.

: Bearbeitet durch User
von Harald K. (kirnbichler)


Lesenswert?

Steve van de Grens schrieb:
> Ha, aber noch teurer als mit Windows.

Nicht beim Kistenschieber.

Zurück zur Diskussion:

Wer darauf besteht, unixoide Makefiles unter Windows zu verwenden, muss 
entweder eine unixoide Umgebung dafür schaffen, oder sich die Mühe 
machen, die Makefiles portabel zu gestalten.

Das ist, wenn man sich drauf einlässt, keine Raketenwissenschaft.
1
ifeq ($(OS),Windows_NT)
2
  RM = del
3
  PATHSEP = \
4
else
5
  RM = rm
6
  PATHSEP = /
7
endif
8
9
TARGET = main
10
11
CC = gcc
12
CFLAGS = -g -Wall -O0
13
14
CPPFLAGS =
15
LDFLAGS =
16
17
PATH_MAIN = ..$(PATHSEP)src
18
PATH_MODULE = $(PATH_MAIN)$(PATHSEP)module
19
20
# source files
21
SOURCES_MAIN = $(PATH_MAIN)$(PATHSEP)main.c
22
SOURCES_MODULE = $(PATH_MODULE)$(PATHSEP)fun_1$(PATHSEP)fun_1.c
23
SOURCES = $(SOURCES_MAIN) $(SOURCES_MODULE)
24
BUILD_DIR := ..$(PATHSEP)out
25
OBJECTS = $(SOURCES:.c=.o)  
26
27
$(TARGET) : $(OBJECTS)
28
  $(CC) $(CFLAGS) -o $@ $^ $(LDFLAGS) 
29
30
.PHONY: clean
31
clean:
32
  RM $(OBJECTS)

Man kann sich natürlich auch hinstellen und jahrzehntelang herumheulen, 
wie schlecht die Welt und wie falsch alles außer Linux ist.

von Udo K. (udok)


Lesenswert?

Harald K. schrieb:
> ifeq ($(OS),Windows_NT)
>   RM = del
>   PATHSEP = \

Wenn du hier schon gmake eigene Abfragen verwendest, dann wird das 
nichts.
Da ist es einfacher, die WSL2 oder MSYS2 zu installieren, und sich mit 
den Linux Problemen unter Windows herumzuärgern :-)

von Monk (roehrmond)


Lesenswert?

Udo K. schrieb:
> Da ist es einfacher, die WSL2 oder MSYS2 zu installieren,

Oder ganz klassisch CygWin

von Udo K. (udok)


Lesenswert?

Steve van de Grens schrieb:
> Oder ganz klassisch CygWin

Ah ja, das gibts ja auch noch. Was für eine Freude, wenn dann die 
statisch gelinkten Programme nicht gehen, weil der gcc noch eine 
dämliche Startup Lib dynamisch dazulinkt.  Und Programme, die kompatibel 
zu Windows Exception Handling sind?  Vergiss es.

: Bearbeitet durch User
von Oliver S. (oliverso)


Lesenswert?

Steve van de Grens schrieb:
> Udo K. schrieb:
>> Da ist es einfacher, die WSL2 oder MSYS2 zu installieren,
>
> Oder ganz klassisch CygWin

Das war mal 1897 oder so angesagt. Klassisch halt. Braucht und will aber 
doch heutzutage kein Mensch mehr…

Oliver

: Bearbeitet durch User
von Monk (roehrmond)


Lesenswert?

Oliver S. schrieb:
> Braucht und will aber doch heutzutage kein Mensch mehr…

Auf der Arbeit haben wir noch ein paar alte Softwareprojekte mit Build 
Scripten, die für Linux gedacht waren. Ein paar Entwickler hängen aber 
so sehr an Windows, dass sie nicht mal mit WSL zurecht kommen. Für die 
ist CygWin optimal, denn damit laufen unsere Scripte alle "einfach so".

Inzwischen stellen wir nur noch Leute ein, die zumindest Grundkenntnisse 
über Linux mitbringen. Wir könnten eher auf Windows Know-How verzichten.

von Klaus H. (klummel69)


Lesenswert?

>Oder ganz klassisch CygWin

Würde ich nicht mehr nehmen. Machte bei mir einige Probleme.
Wenn ich einen gcc Compiler auf der Windows Plattform benötige, nutze 
ich https://winlibs.com/

Hat außer dem Gcc noch alle notwendigen Werkzeuge dabei, ist deutlich 
aktueller als andere Pakete und ist portable/braucht nicht installiert 
zu werden. Entpacken und PATH setzen reicht.

von Harald K. (kirnbichler)


Lesenswert?

Udo K. schrieb:
> Wenn du hier schon gmake eigene Abfragen verwendest, dann wird das
> nichts.

Dann nimm halt 'ne andere Abfrage, ich habe das hier nur 
zusammengetippt, um das eigentliche Problem zu lösen.

> Da ist es einfacher, die WSL2 oder MSYS2 zu installieren, und sich mit
> den Linux Problemen unter Windows herumzuärgern :-)

Klar. Weil die Scheuklappen so eng sitzen, daß man jede Pfadschreibweise 
akzeptiert, die unter Linux die richtige ist, muss man Linux 
installieren ... statt einfach nur ein portables Makefile zu verwenden.


Die Abfrage am Anfang lässt sich sicherlich besser machen (man könnte 
eine Umgebungsvariable auswerten, die unter Windows immer existiert oder 
halt irgendwas was anderes anstellen)

Bekommt man das nicht hin, ließe sich der Kram am Anfang des Makefiles 
auch in zwei Zeilen fest codieren, und der Rest macht dann das, was er 
soll: Funktionieren. Ohne, daß man sich ein Linux oder sonstwas 
installieren muss.

Das eigentliche Problem ist trivial, und trivial simpel gelöst.

von Rolf M. (rmagnus)


Lesenswert?

Nicht Joachim B. schrieb:
> Alle Linux Versionen nutzen standardmäßig eine Bourne Shell oder eine
> dazu kompatible.

Für die Login-Shell ja, aber nicht für die, mit der Skripte ausgeführt 
werden. Gerade in make kommt z.B. unter Debian die dash zu Einsatz.

von Monk (roehrmond)


Lesenswert?

Rolf M. schrieb:
> Gerade in make kommt z.B. unter Debian die dash zu Einsatz.

Die dash ist zur Bourne Shell kompatibel. Scripte die damit nicht 
funktionieren, sind nicht zur Bourne Shell kompatibel. Sie sollten dann 
auch nicht mit #!/bin/sh beginnen, sondern mit dem Namen der Shell, für 
die sie geschrieben wurden.

Udo K. schrieb:
> sh auf Debian ist nicht kompatibel mit der sh in Ubuntu

Die Inkompatibilität liegt in den betroffenen Scripten, nicht in den 
Shells und auch nicht in Ubuntu vs. Debian. Nervig ist es für betroffene 
trotzdem. Ich kann deinen Frust nachvollziehen.

: Bearbeitet durch User
von Rolf M. (rmagnus)


Lesenswert?

Nicht Joachim B. schrieb:
> Rolf M. schrieb:
>> Gerade in make kommt z.B. unter Debian die dash zu Einsatz.
>
> Die dash ist zur Bourne Shell kompatibel.

Ja, ok, Bourne Shell. Ich hatte an die bash gedacht.

> Scripte die damit nicht funktionieren, sind nicht zur Bourne Shell
> kompatibel. Sie sollten dann auch nicht mit #!/bin/sh beginnen, sondern
> mit dem Namen der Shell, für die sie geschrieben wurden.

Ich spreche nicht nur von Skripten, sondern von Shell-Kommandos, die 
direkt im Makefile stehen, ganz ohne Shebang, das man dort ja auch gar 
nicht angeben kann. Diese werden unter Debian defaultmäßig mit der dash 
ausgeführt.

: Bearbeitet durch User
von Daniel A. (daniel-a)


Lesenswert?

Rolf M. schrieb:
> Ich spreche nicht nur von Skripten, sondern von Shell-Kommandos, die
> direkt im Makefile stehen, ganz ohne Shebang, das man dort ja auch gar
> nicht angeben kann. Diese werden unter Debian defaultmäßig mit der dash
> ausgeführt.

In GNU Make kann man die über die SHELL variable setzen. Auch direkt aus 
dem Makefile. Beispiel:
1
# Wit schreiben das Makefile in Python!
2
SHELL=/usr/bin/python3
3
# Wir wollen keine neue Shell für jede Zeile
4
.ONESHELL:
5
6
hello:
7
  message = "Hello Python!"
8
  print(message)

von Rbx (rcx)


Lesenswert?

Chandler B. schrieb:
> ich habe ein kleines Projekt (in C unter Windows10), welches ich gerne
> mit make bauen möchte.

Ja schön, und welches Compilerpacket? Man nimmt entweder native 
Entwicklungswerkzeuge, wie das normale VS oder z.B. Watcom C oder 
Linux/Unix-Importhilfen.

Für Linux-Imports gibt es fertige (und bewährte) Packete (s.o.) mit 
Runtimes oder Dll-Ersatz, VMs und weiß der Geier, was noch (s.o.) - 
früher gab es die Haskell Plattform, die konnte man auch missbrauchen.
Bei Windows 10 gibt es immerhin das WSL - auf jedenfall schon mal etwas 
gutes zum Nachlesen in diesem Zusammenhang.

von Monk (roehrmond)


Lesenswert?

Rbx schrieb:
> Ja schön, und welches Compilerpacket

Lies doch erst mal den Thread durch, bevor du antwortest. Das Problem 
wurde längst beschrieben und gelöst. Dein Lösungsansatz ist für 
irgendein anderes Problem, aber nicht für das hier.

: Bearbeitet durch User
von Rbx (rcx)


Lesenswert?

Monk schrieb:
> Das Problem
> wurde längst beschrieben und gelöst.

Ach ja? Der TE hat sich bisher nicht zurückgemeldet. Der Thread gibt 
allenfalls Auskunft darüber, das viele Leute sich bereits mit Linux in 
Windows und Windows in Linux ganz gut auskennen.
Der Threadstarter selber scheint sich mit solchen Thematiken noch nicht 
groß auseinandergesetzt haben, denn dann wäre eine konkretere Frage zu 
einem konkreten Entwicklungspacket angesagt gewesen, welche auch nicht 
immer im Plug und Play-Sinne gleich funktionieren.

Eine andere Sache ist, dass normalerweise die meisten wichtigen Sachen 
in der Dokumentation vom Entwicklungssystem stehen.
Man könnte jetzt auch LLVM einsetzen 
(https://llvm.org/docs/GettingStartedVS.html) oder von mir aus Tiny C 
(https://bellard.org/tcc/tcc-doc.html) -  man wird aber auch diese 
konkret referenzieren müssen, wenn Probleme auftauchen.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.