c - 从cmd行读取命令,并在C中执行它们

标签 c unix command-line execv

我正在编写一个程序来从命令行(linux/unix 命令)获取用户输入,并在我的程序中执行它们。

到目前为止我的步骤:

  1. 询问用户输入的命令数量
  2. Fork() 创建子进程
  3. 输出子PID和父PID
  4. 允许用户输入每个命令,将每个输入读取到argv的索引中
  5. 使用 execv 运行 argv 内的每个命令

主要问题是,当它执行时,它只执行 execv 命令中的“bin/ls/”。

这是运行我的程序的示例输出:

输入命令数量:2
子进程的 PID 为 3487。父进程的 PID 为 3485
输入 UNIX 命令:ls
输入 UNIX 命令:-al

在 CMD 行上键入“LS”时的文件列表

流程完成。


这是我的源代码:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>

void main(int argc, char *argv[20])
{
        int pid;
        int num = 0;

        printf("Enter number of commands: ");
        scanf("%d", &argc);

        pid = fork();

        if(pid == 0)
        {
                printf("Child's PID is %d. Parent's PID is %d\n", (int)getpid(), (int)getppid());

                for(num=0; num < argc; num++)
                {
                        printf("Enter a UNIX command: ");
                        scanf("%s", argv[num]);
                }

                argv[num+1] = 0;

                execv("bin/ls/", argv);
        }
        else
        {
                wait(pid);
                printf("Process Complete.\n");
                exit(0);
        }
}

最佳答案

首先,您在 main 中定义 char* argv[20] 这不是一个好主意。如果您传入超过 20 个参数,您将超出数组的范围。

其次,您正尝试使用 scanf("%s", argv[num]) 将字符串读取到据我所知尚未初始化的地址空间中。

“字符串”的 argv[] 数组在调用程序时由操作系统初始化,如果您不向程序传递任何参数,则不会有任何“字符串”,这意味着您将写入您可能不拥有的随机内存。

如果您确实想按照现在的方式加载命令,请尝试以下操作:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>

void main(int argc, char *argv[])
{
    int pid;
    int num = 0;
    int argc2 = 0;
    char* argv2[20]; // argv2 will point inside of buffer for convenience.
    char* buffer[2000]; // note each array has a limit of 100 characters.

    printf("Enter number of commands: ");
    scanf("%d", &argc2);

    pid = fork();

    if(pid == 0)
    {
            printf("Child's PID is %d. Parent's PID is %d\n", (int)getpid(), (int)getppid());

            for(num=0; num < argc2 && num < 20; num++) // your array is 20 long
            {
                    argv2[num] = &buffer[num * 100];
                    printf("Enter a UNIX command: ");
                    scanf("%s", argv2[num]);
            }

            argv[num] = 0; // no need to add + 1 because the for loop did already anyway.

            execv("Assignments/ls", argv2);
    }
    else
    {
            wait(pid);
            printf("Process Complete.\n");
            exit(0);
    }
}

或者,您可以将参数传递给主程序,主程序只需将它们传递给被调用的程序,如下所示:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>

void main(int argc, char *argv[])
{
    int pid;
    int num = 0;

    printf("You entered %d commands: \n", argc);

    for (num = 0; num < argc; ++num)
    {
        printf("\t%s\n", argv[num]);
    }

    pid = fork();

    if(pid == 0)
    {
            printf("Child's PID is %d. Parent's PID is %d\n", (int)getpid(), (int)getppid());

            execv("Assignments/ls", &argv[1]);
    }
    else
    {
            wait(pid);
            printf("Process Complete.\n");
            exit(0);
    }
}

关于c - 从cmd行读取命令,并在C中执行它们,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12539223/

相关文章:

C:提前分配内存还是按需分配内存?

macos - 苹果电脑 : Lack of --printf for stat

c - 使用c中的线程对矩阵中的元素求和

linux - 如何在 N 行内 grep 多个字符串

c - 如何将命令行参数传递给 C 函数

c - 复合文字中的字符串文字

c - 使用结构体和数组编写函数

internet-explorer - 通过命令行清除浏览器缓存

c - 为什么 while 中的 getchar 在第一次迭代后不执行?

linux - curl 中的 -v verbose 有什么区别?