/ Forside / Teknologi / Udvikling / C/C++ / Nyhedsindlæg
Login
Glemt dit kodeord?
Brugernavn

Kodeord


Reklame
Top 10 brugere
C/C++
#NavnPoint
BertelBra.. 2425
pmbruun 695
Master_of.. 501
jdjespers.. 500
kyllekylle 500
Bech_bb 500
scootergr.. 300
gibson 300
molokyle 287
10  strarup 270
Header-filer!
Fra : Preben Holm


Dato : 09-03-04 19:55

Hej alle

Jeg har forsøgt at forstå header-filer og deres funktion og troede
endelig jeg havde set lyset, men nu er solen vist gået ned igen.

Jeg har kigget på linux-kernens header-filer (og jeg indrømmer blankt at
det er noget af et step at tage eftersom jeg knap har lavet Hello World
i C før), men anyway, nu skal jeg bruge alt dette her og er derfor nødt
til at tage en udfordring op.

Så vidt jeg havde forstået skulle der for hver header-fil være en C-fil
som indeholdt de funktioner der var defineret i header-filen, men det
har jeg så også fundet ud af at dette ikke er rigtigt, da jeg har kigget
på linux-kernen... Derimod har jeg også lært at man kan inkludere andre
header-filer i selve header-filen selv, og at disse så kan indeholde de
funktioner jeg leder efter! Men nu er problemet så, at disse filer kan
jeg bare overhovedet ikke finde - er der nogen der har en anvisning
eller f.eks. en forklaring på hvorfor?

Jeg har endvidere set at man kan inkludere header-filen i selve
header-filen selv - hvad har det af betydning?

Altså, hvis vi nu tager f.eks. cpu.h-headeren:
;----------------------------------------------------------------------
#ifndef _ASM_I386_CPU_H_
#define _ASM_I386_CPU_H_

#include <linux/device.h>
#include <linux/cpu.h>
#include <linux/topology.h>

#include <asm/node.h>

struct i386_cpu {
struct cpu cpu;
};
extern struct i386_cpu cpu_devices[NR_CPUS];


static inline int arch_register_cpu(int num){
struct node *parent = NULL;

#ifdef CONFIG_NUMA
parent = &node_devices[cpu_to_node(num)].node;
#endif /* CONFIG_NUMA */

return register_cpu(&cpu_devices[num].cpu, num, parent);
}

#endif /* _ASM_I386_CPU_H_ */
;----------------------------------------------------------------------


og inkluderer altså headerfilen selv. Hvad er meningen med det?

Og spørgsmålet er så endvidere hvor finder jeg funktionen
arch_register_cpu(int num) henne?



På forhånd tak..

Mvh / Preben Holm

 
 
Byrial Jensen (09-03-2004)
Kommentar
Fra : Byrial Jensen


Dato : 09-03-04 21:03

Preben Holm wrote:
> Jeg har kigget på linux-kernens header-filer (og jeg indrømmer blankt at
> det er noget af et step at tage eftersom jeg knap har lavet Hello World
> i C før),

Ja, det unægteligt en ordentlig mundfuld at starte med Linux-kernen som
er et meget atypisk C-program.

> Så vidt jeg havde forstået skulle der for hver header-fil være en C-fil
> som indeholdt de funktioner der var defineret i header-filen, men det
> har jeg så også fundet ud af at dette ikke er rigtigt, da jeg har kigget
> på linux-kernen...

Sådan er det tit, men det er ikke et krav at det er på den måde.

For at forstå headerfiler, skal man først forstå C's præprocessor. Når
man oversætter et C-program, bliver programmet først behandlet af
præprocessoren[1] som behandler alle præprocessor-direktiverne, som er
de linjer der begynder med "#" herunder #include-direktiverne. Et
#include-direktiv vil indlæse den refererede fil og indsætte indholdet
på direktivets plads[2]. Det betyder at hvis headerfilen indeholder for
eksempel funktionsprototyper, at disse funktionsprototyper vil være
erklærede i den samlede oversættelsesenhed[3] før funktionerne bruges.

[1] I hvert fald idemæssigt. I praksis kan præprocessoren godt være helt
integreret i resten af oversætteren, og forbehandlingen kan godt ske
samtidig med resten af oversættelsen.

[2] Dette gælder ikke nødvendigvis i C++. Her vil #include-direktiver
ikke nødvendigvis referere til en fysisk fil.

[3] En oversættelsesenhed er resultatet af forbehandlingen hvor blandt
andet alle #include-direktiver er udført.

> Derimod har jeg også lært at man kan inkludere andre
> header-filer i selve header-filen selv, og at disse så kan indeholde de
> funktioner jeg leder efter!

Ja, man kan gøre alt i en headerfil som man også kan i selve C-filen,
herunder inkludere andre headere.

> Men nu er problemet så, at disse filer kan
> jeg bare overhovedet ikke finde - er der nogen der har en anvisning
> eller f.eks. en forklaring på hvorfor?

Hvis man bruger direktivet

#include "somefile.h"

skal man lede efter somefile.h samme sted som den fil man aktuelt er ved
behandle. Hvis man derimod bruger formen

#include <somefile.h>

er der tale en systemfil som oversætteren finder på forudbestemte
implementationsafhængige steder. Standardplacering på unix'er (herunder
Linux) er /usr/include/somefile.h. Man kan også ofte give særlige
instruktioner til oversætteren for eksempel på kommandolinjen om
placeringen af sådanne filer når man oversætter.

> Jeg har endvidere set at man kan inkludere header-filen i selve
> header-filen selv - hvad har det af betydning?

Det gør man ikke (i hvert fald ikke ubetinget) fordi det ville give en
uendelig løkke.

> Altså, hvis vi nu tager f.eks. cpu.h-headeren:
> ;----------------------------------------------------------------------
> #ifndef _ASM_I386_CPU_H_
> #define _ASM_I386_CPU_H_
>
> #include <linux/device.h>
> #include <linux/cpu.h>
> #include <linux/topology.h>
>
> #include <asm/node.h>
> [...]

> og inkluderer altså headerfilen selv. Hvad er meningen med det?

Det gør den ikke. Jeg har ikke p.t. installeret Linux-kildeteksten, men
<linux/cpu.h> må referere til en anden fil end du citerer fra. Bemærk at
<linux/cpu.h> skal søges i kataloget "linux" som er på en foruddefineret
plads for systemfiler.

> Og spørgsmålet er så endvidere hvor finder jeg funktionen
> arch_register_cpu(int num) henne?

Den finder du i den headerefil du citerede fra. Lige her:

> static inline int arch_register_cpu(int num){
> struct node *parent = NULL;
>
> #ifdef CONFIG_NUMA
> parent = &node_devices[cpu_to_node(num)].node;
> #endif /* CONFIG_NUMA */
>
> return register_cpu(&cpu_devices[num].cpu, num, parent);
> }

Det er en fuldt definition af funktionen, så den er ikke også andre steder.




Preben Holm (10-03-2004)
Kommentar
Fra : Preben Holm


Dato : 10-03-04 00:02

>> Jeg har kigget på linux-kernens header-filer (og jeg indrømmer blankt
>> at det er noget af et step at tage eftersom jeg knap har lavet Hello
>> World i C før),
>
>
> Ja, det unægteligt en ordentlig mundfuld at starte med Linux-kernen som
> er et meget atypisk C-program.

Hvorfor er det et atypisk C-program?



>> Altså, hvis vi nu tager f.eks. cpu.h-headeren:
>> ;----------------------------------------------------------------------
>> #ifndef _ASM_I386_CPU_H_
>> #define _ASM_I386_CPU_H_
>>
>> #include <linux/device.h>
>> #include <linux/cpu.h>
>> #include <linux/topology.h>
>>
>> #include <asm/node.h>
>> [...]
>
>
>> og inkluderer altså headerfilen selv. Hvad er meningen med det?
>
>
> Det gør den ikke. Jeg har ikke p.t. installeret Linux-kildeteksten, men
> <linux/cpu.h> må referere til en anden fil end du citerer fra. Bemærk at
> <linux/cpu.h> skal søges i kataloget "linux" som er på en foruddefineret
> plads for systemfiler.

Ja ok... filen ligger selvfølgelig ikke lige i include-biblioteket, så
det er nok derfor... (bare ifølge min mening ikke så smart at bruge
samme filnavn *gg*)


> Den finder du i den headerefil du citerede fra. Lige her:
>
>> static inline int arch_register_cpu(int num){
>> struct node *parent = NULL;
>>
>> #ifdef CONFIG_NUMA
>> parent = &node_devices[cpu_to_node(num)].node;
>> #endif /* CONFIG_NUMA */
>>
>> return register_cpu(&cpu_devices[num].cpu, num, parent);
>> }
>
>
> Det er en fuldt definition af funktionen, så den er ikke også andre steder.

Ja ok... det er det med at åbne øjnene :)


Takker...


Mvh / Preben

Per Abrahamsen (10-03-2004)
Kommentar
Fra : Per Abrahamsen


Dato : 10-03-04 09:03

Preben Holm <64bitNOSPAM@mailme.dk> writes:

> Hvorfor er det et atypisk C-program?

Blandt andet fordi at kernen ikke bruger C standard biblioteket, så
der er en stor del af det vi normalt kalder C der ikke er til
rådighed. Der gør mange ting betydeligt mere komplicerede.

Linux kernens formål er faktisk i høj grad at gøre livet lettere for C
biblioteket, og derved for "almindelige" C programmer.

Søg
Reklame
Statistik
Spørgsmål : 177549
Tips : 31968
Nyheder : 719565
Indlæg : 6408820
Brugere : 218887

Månedens bedste
Årets bedste
Sidste års bedste