English 中文(简体)
C项职能的履行
原标题:Array of functions in C

I am working on a project where I have to implement a handler for several functions, all of which have a number associated with them. The number that they are associated with is how the different functions are called. Knowing this I want to be able to group them into an array using the number as the index to the functions. The problem is, arrays need to have the same type of elements inside of them right? so how can I place these functions into an array?

这些职能是怎样编号的:

enum 
  {
    SYS_HALT,                   /* Halt the operating system. */
    SYS_EXIT,                   /* Terminate this process. */
    SYS_EXEC,                   /* Start another process. */
    SYS_WAIT,                   /* Wait for a child process to die. */
    SYS_CREATE,                 /* Create a file. */
    SYS_REMOVE,                 /* Delete a file. */
    SYS_OPEN,                   /* Open a file. */
    SYS_FILESIZE,               /* Obtain a file s size. */
    SYS_READ,                   /* Read from a file. */
    SYS_WRITE,                  /* Write to a file. */
    SYS_SEEK,                   /* Change position in a file. */
    SYS_TELL,                   /* Report current position in a file. */
    SYS_CLOSE,                  /* Close a file. */
  };

And here is the list of function prototypes:

void halt (void) NO_RETURN;
void exit (int status) NO_RETURN;
pid_t exec (const char *file);
int wait (pid_t);
bool create (const char *file, unsigned initial_size);
bool remove (const char *file);
int open (const char *file);
int filesize (int fd);
int read (int fd, void *buffer, unsigned length);
int write (int fd, const void *buffer, unsigned length);
void seek (int fd, unsigned position);
unsigned tell (int fd);
void close (int fd);

www.un.org/sc/ctc

将所有职能纳入C的阵列或其他数据结构是否容易?

任何帮助都值得赞赏,这是对学校项目的支持,因此,一个小的例子或联系将非常有用,但我愿意自己制定解决办法。

增 编

www.un.org/Depts/DGACM/index_spanish.htm Edit:我想做些什么?

我想能够确定一些阵列,并按批次数的索引储存一个功能点。

//I don t know how to handle the type here
<some_type> system_call_arr[128];

system_call_arr[SYS_HALT] = halt;
system_call_arr[SYS_EXIT] = exit;
system_call_arr[SYS_EXEC] = exec;

// and so on....

www.un.org/Depts/DGACM/index_spanish.htm Edit 2

自2006年以来 Ben说,所有论点都符合32点论点,因此,我不能这样界定:

typedef int (*sys_func) (uint32_t, uint32_t, uint32_t);
sys_func syscall_array[128];

syscall_array[SYS_HALT] = (sys_func)halt;
//etc....

是否像这种良好做法一样?

最佳回答

The classic UNIX way to do this is to give all of those functions the same signature (say int sys_func(struct args *a) and then put those all into a function array. When you marshal arguments for the calls you just put them in as arg1, arg2, etc all in struct args and each syscall uses them differently. Or you can alias a special structure on top of it to give them meaningful names.

在您的问答中,“这种良好做法是什么样?” 我就你的问题作了回答,这似乎是执行一个简单的运作系统。 运行系统必须采用从来都不应正常应用的方式加以协调。 它可以使用有关字数的假设(例如,所有字数都是32比值,如ILP-32),并了解有关ABI ,因为执行这些物品是操作系统工作的一部分。 如果您的顾问办公室能够进入其他平台,它将以诸如<条码>、<>条码/代码”等不同内容汇编成册,处理这些案件。

Why did I suggest struct args rather than your method? Because in an operating system you will have a few layers between the user making the syscall and the actual code running from your function pointer table. If you pass these arguments explicitly through each layer you are going to copy them several times. If the first layer can simply provide a pointer that sort of "jumps" the arguments over the intermediate functions. If you re dealing with an ABI where the calling convention is to push arguments on the stack, you can avoid copying the arguments altogether and just take an appropriate stack address as the args.

您可在上找到关于这一方面的讨论,在操作系统设计的每一个其他方面都这样做。 The Design and Implementation of the 4.4 BSDOperation System by McKusick et al. 如果你能够找到老的4.3<>>>>>/em>版本,它实际上是一个相当温和的体积,仍然与你重新工作完全相关。

问题回答

On any modern system, you can just create an array of void* to hold the function pointers. But, that s technically undefined behaviour in ANSI C. Instead, you can use a generic function pointer type like void(*)() and cast the pointer to the correct function pointer type when it s called See the C FAQ. But you re going to need a switch statement anyway to do that cast, so as Jesus mentions, you can just call the correct function at the same time and forget the array altogether.

确实没有必要,除非你重新做提供接口的东西,而且通常是为了你制造一个能够执行和确定适当点的基本业务的构件。 就象这样的东西(如果你不试图使其具有通用性的话)而言,只是就大价值使用开关声明。 在C,由于所有面值都依次成形,因此大部分时间优化到跳板上来,因此,在检查根据某些请求参数执行哪些职能时,你不会陷入瘫痪状态。

例如,在Lino Kernel, 有一些基本的运作结构,这些结构有预设的职能模式,而你们都必须这样做,就是履行这些职能,输出一个具有适当职能要素的构件,供你执行,并pl起和发挥,但似乎这样做会超出你所希望的。

If you are willing to eschew type safety, you can create a union type, like so:

union Args {
    size_t st;
    ssize_t sst;
    int i;
    unsigned u;
    pid_t pt;
    mode_t mt;
    char *pc;
    const char* cpc;
    void *pv;
    const void *cpv;
    /* etc */
};

然后,就每项职能而言,它们都接受<代码>union Args *作为参数清单,并接受size_t,作为参数数目(开放可以接受3个参数——它使用va_* 视需要加以核对)。 回到<代码>union Args。

注:<代码> 撤销的功能,仅有<代码>return 0。

E.g.

union Args my_open(union Args *args, size_t nargs) {
    union Args a;
    switch (nargs) {
    case 2:
        a.i = open(args[0].cpc, args[1].i);
        break;
    case 3:
        a.i = open(args[0].cpc, args[1].i, args[2].mt);
        break;
    default:
         errno = EINVAL;
         a.i = -1;
    }
    return a;
}

然后,你可以有以下几条内容:

typedef union Args (*My_func)(union Args *, size_t);
My_func *fptrs;




相关问题
Fastest method for running a binary search on a file in C?

For example, let s say I want to find a particular word or number in a file. The contents are in sorted order (obviously). Since I want to run a binary search on the file, it seems like a real waste ...

Print possible strings created from a Number

Given a 10 digit Telephone Number, we have to print all possible strings created from that. The mapping of the numbers is the one as exactly on a phone s keypad. i.e. for 1,0-> No Letter for 2->...

Tips for debugging a made-for-linux application on windows?

I m trying to find the source of a bug I have found in an open-source application. I have managed to get a build up and running on my Windows machine, but I m having trouble finding the spot in the ...

Trying to split by two delimiters and it doesn t work - C

I wrote below code to readin line by line from stdin ex. city=Boston;city=New York;city=Chicago and then split each line by ; delimiter and print each record. Then in yet another loop I try to ...

Good, free, easy-to-use C graphics libraries? [closed]

I was wondering if there were any good free graphics libraries for C that are easy to use? It s for plotting 2d and 3d graphs and then saving to a file. It s on a Linux system and there s no gnuplot ...

Encoding, decoding an integer to a char array

Please note that this is not homework and i did search before starting this new thread. I got Store an int in a char array? I was looking for an answer but didn t get any satisfactory answer in the ...