命令解释器c语言

当我是 白痴 好了,什么是C语言的解释器

解释器(英语:Interpreter),又译为直译器,是一种电脑程序,能够把高级编程语言一行一行直接转译运行

预编译器的不同在于它逐行解释运行,与解释执行语言如python相似

命令解释器c语言

求解释代码,有关用c语言写一个简单的shell解释器的

#include stdio.h

#include stdlib.h

#include string.h

#include fcntl.h

#include unistd.h

#include sys/wait.h

#define CMD_LINE 1024

#define PIPE_MAX 16

#define ARG_MAX 10

typedef struct {

    char *arg[ARG_MAX];

    char *in;

    char *out;

} cmd_t;

extern int parse_token(char *buf, cmd_t cmd[]);

extern int parse(char *buf, cmd_t * cmd);

extern int test_parse(cmd_t cmd[], int len);

int main(int argc, char *argv[])

{

    char buf[CMD_LINE];

    cmd_t cmd[PIPE_MAX + 1];

    int fd[PIPE_MAX][2];

    int j, i;

    int cmd_len, pipe_len;

    pid_t pid;

    while (1) {

        printf(“my_shell#”);        //打印提示符

       

        fgets(buf, CMD_LINE, stdin);        //获得输入

        buf[strlen(buf) – 1] = ‘\0’;        //去掉结尾的换行符?

        cmd_len = parse_token(buf, cmd);//解析命令

        pipe_len = cmd_len – 1;                 //

        if (pipe_len PIPE_MAX)

            continue;

        for (i = 0; i pipe_len; ++i)

            pipe(fd[i]);                                    //创建pipe_len个管道

        for (i = 0; i cmd_len; ++i)        //创建cmd_len个进程

            if ((pid = fork()) == 0)            //判断是否为子进程

                break;                                          //如果是子进程,跳出for循环

        if (pid == 0) {                                 //循环中是子进程代码

            if (pipe_len) {

                if (i == 0) {                               //第一个子进程

                    close(fd[i][0]);                    //关闭管道的读取端

                    dup2(fd[i][1], 1);              //复制管理的写入端为标准输出(标准输出会写入管道)

                    close(fd[i][1]);                    //关闭管道的写入端

                    for (j = 1; j pipe_len; ++j)

                        close(fd[j][0]),                //关闭无关进程的管道

                            close(fd[j][1]);

                } else if (i == pipe_len) { //第pipe_len个子进程

                    close(fd[i – 1][1]);            //关闭管道的写入端

                    dup2(fd[i – 1][0], 0);      //复制管理的读取端为标准输出(标准输入会读取管道)

                    close(fd[i – 1][0]);            //关闭管道的读取端

                    for (j = 0; j pipe_len – 1; ++j)

                        close(fd[j][0]),                //关闭无关进程的管道

                            close(fd[j][1]);

                } else {                                        //其他子进程

                    dup2(fd[i – 1][0], 0);      //复制管理的读取端为标准输出(标准输入会读取管道)

                    close(fd[i][0]);                    //关闭管道的读取端

                    dup2(fd[i][1], 1);              //复制管理的写入端为标准输出(标准输出会写入管道)

                    close(fd[i][1]);                    //关闭管道的写入端

                    for (j = 0; j pipe_len; ++j) {

                        if ((j != i – 1)                //关闭无关进程的管道

                            || (j != i))

                            close(fd[j][0]),

                                close(fd[j]

                                  [1]);

                    }

                }

            }

            if (cmd[i].in) {        //如果需要,打开输入文件并重定向

                int fd = open(cmd[i].in, O_RDONLY);

                dup2(fd, STDIN_FILENO);

                close(fd);

            }

            if (cmd[i].out) {       //如果需要,打开输出文件并重定向

                int fd =

                    open(cmd[i].out,

                     O_RDWR | O_CREAT | O_TRUNC, 0644);

                dup2(fd, STDOUT_FILENO);

                close(fd);

            }

            execvp(cmd[i].arg[0], cmd[i].arg);  //执行当前命令

            fprintf(stderr, “Failed exec\n”);       //执行命令失败后才会执行之后的代码

            exit(127);

        }       //子进程代码结束

        /* parent  */

        for (i = 0; i pipe_len; ++i)

            close(fd[i][0]), close(fd[i][1]);

        for (i = 0; i cmd_len; ++i)

            wait(NULL);     //等待子进程结束

    }

    return 0;

}

int parse_token(char *buf, cmd_t cmd[])

{

    int n = 0;

#if 1

    char *save_p;

    char *p = strtok_r(buf, “|”, save_p);//以’|’分割命令将分割后的第一部分给p

    while (p != NULL) {

        parse(p, cmd[n++]);

        p = strtok_r(NULL, “|”, save_p);//将之后的部分给p,每次给一部分,每调用一次给下一部分

    }

#else               //下一块语句不被执行

    cmd[n].arg[0] = “ls”;

    cmd[n].arg[1] = “-l”;

    cmd[n].arg[2] = NULL;

#endif

    return n;

}

int test_parse(cmd_t cmd[], int len)        //此函数未被调用

{

    int i;

    for (i = 0; i len; ++i) {

        printf(“cmd[%d]:”, i);

        int j = 0;

        while (cmd[i].arg[j])

            printf(” %s”, cmd[i].arg[j++]);

        if (cmd[i].in)

            printf(“\tin:%s”, cmd[i].in);

        if (cmd[i].out)

            printf(“\tout:%s”, cmd[i].out);

        printf(“\n”);

    }

    return 0;

}

int parse(char *buf, cmd_t * cmd)

{

    int i = 0;

    cmd-in = NULL;

    cmd-out = NULL;

    char *p = strtok(buf, ” “);//以空格分割命令(此时命令已被|分割过了)

    while (p) {

        if (*p == ”) {         //如果命令以开头,即需要做输入重定向

            if (*(p + 1))                   //这种情况是后无空格直接跟文件名

                cmd-in = p + 1;

            else                                    //这种情况是后有空格

                cmd-in = strtok(NULL, ” “);

        } else if (*p == ”) {  //如果命令以开头,即需要做输出重定向

            if (*(p + 1))                   //这种情况是后无空格直接跟文件名

                cmd-out = p + 1;

            else                                    //这种情况是后有空格

                cmd-out = strtok(NULL, ” “);

        } else

            cmd-arg[i++] = p;       //这种情况是正常命令或参数

        p = strtok(NULL, ” “);

    }

    cmd-arg[i] = NULL;

    return 0;

}

如何用C语言实现C的解释器

将C语言翻译成“汇编”塞到内存里,然后用“虚拟机”来跑这段汇编。

因此我们需要的东西是:

一个虚拟机:用来跑下面这种汇编。

一种汇编:用来描述原来的C语言。

一个“翻译器”:将C语言翻译成上面这种汇编。

c语言cmd窗口在哪

m.wangchao.net.cn

推荐

cmd窗口是什么,怎么打开

举报/纠错

分类: 电脑/网络 操作系统/系统故障

参考答案:

cmd是command的缩写.命令行

在9x系统下输入command就可以打开命令行.而在NT系统上可以输入cmd来打开.

在命令行里你可以看到你的系统版本,文件系统版本等等

你可以敲入help查看帮助

Cmd启动命令解释器 Cmd.exe 的新实例。如果在不含参数的情况下使用,则 cmd 显示 Windows XP 的版本和版权信息。

语法

cmd [[{/c|/k}] [/s] [/q] [/d] [{/a|/u}] [/t:fg] [/e:{on|off}] [/f:{on|off}] [/v:{on|off}] string]

参数

/c

执行 string 指定的命令,然后停止。

/k

执行 string 指定的命令并继续。

/s

修改位于 /c 或 /k 之后的 string 处理。

/q

关闭回显。

/d

禁用自动运行命令执行。

/a

创建美国国家标准协会 (ANSI) 输出。

/u

创建 Unicode 输出。

/t:fg

设置前景 f 和背景 g 的颜色。下表列出了可用作 f 和 g 的值的有效十六进制数字。 值 颜色

0 黑色

1 蓝色

2 绿

3 湖蓝色

4 红

5 紫色

6 黄

7 白色

8 灰色

9 浅蓝色

A 浅绿色

B 浅水绿

C 浅红色

D 浅紫色

E 浅黄色

F 亮白色

/e:on

启用命令扩展。

/e:off

禁用命令扩展。

/f:on

启用文件和目录名完成。

/f:off

禁用文件和目录名完成。

/v:on

启用延迟的环境变量扩展。

/v:off

禁用延迟的环境变量扩展。

string

指定要执行的命令。

/?

在命令提示符显示帮助。

注释

使用多个命令

可以在 string 中使用由 分隔的多个命令,不过这些命令必须置于引号之中(例如,”commandcommandcommand”)。

处理引号

如果指定了 /c 或 /k,则在满足下述所有条件的情况下,cmd 会处理 string 中的其余命令而将引号保留:

未使用 /s。

正确使用一对引号。

在引号内未使用任何特殊字符(例如: ( ) @ ^ |}。

在引号内使用了一个或多个空格子符。

引号内的 string 为可执行文件的名称。

如果上述条件不能满足,则处理 string 时将首先检查它的第一个字符以验证其是否为左引号。如果第一个字符是左引号,则它会与右引号分离开。跟在右引号之后的任何文本都会得到保留。

执行注册表子项

如果在 string 中未指定 /d,Cmd.exe 会查找下述注册表子项:

HKEY_LOCAL_MACHINE\Software\Microsoft\Command Processor\AutoRun\REG_SZ

HKEY_CURRENT_USER\Software\Microsoft\Command Processor\AutoRun REG_EXPAND_SZ

如果上述的一个注册表子项或两个都存在,则会在执行其他变量之前执行它们。

警告

编辑注册表不当可能会严重损坏您的系统。在更改注册表之前,应备份计算机上任何有价值的数据。

启用和禁用命令扩展

在 Windows XP 中,命令扩展在默认情况下是启用的。对于特定过程可以使用 /e:off 将它们禁用。通过设置下述 REG_DWORD 值,可以在计算机上或用户会话中启用或禁用所有 cmd 命令行选项的扩展:

HKEY_LOCAL_MACHINE\Software\Microsoft\Command Processor\EnableExtensions\REG_DWORD

HKEY_CURRENT_USER\Software\Microsoft\Command Processor\EnableExtensions\REG_DWORD

在注册表中使用 Regedit.exe 可以将 REG_DWORD 值设为 0×1(即启用)或 0×0(即禁用)。用户特定设置优先于计算机设置,并且命令行选项优先于注册表设置。

警告

编辑注册表不当可能会严重损坏您的系统。在更改注册表之前,应备份计算机上任何有价值的数据。

启用命令扩展后,会影响到下述命令:

assoc

call

chdir (cd)

color

del (erase)

endlocal

for

ftype

goto

if

mkdir (md)

popd

prompt

pushd

set

setlocal

shift

start(还包括将更改外部命令过程)

有关这些命令的详细信息,请参阅“相关主题”。

启用延迟的环境变量扩展

启用延迟的环境变量扩展,可以使用感叹号字符来替代运行时的环境变量值。

启用文件和目录名完成

默认情况下,禁用文件和目录名完成。对于特定的 cmd 命令处理,可以通过 /f:{on|off} 来启用或禁用该功能。通过设置下述 REG_DWORD 值,可以在计算机上或用户会话中启用或禁用所有 cmd 命令处理的文件和目录名完成:

HKEY_LOCAL_MACHINE\Software\Microsoft\Command Processor\CompletionChar\REG_DWORD

HKEY_LOCAL_MACHINE\Software\Microsoft\Command Processor\PathCompletionChar\REG_DWORD

HKEY_CURRENT_USER\Software\Microsoft\Command Processor\CompletionChar\REG_DWORD

HKEY_CURRENT_USER\Software\Microsoft\Command Processor\PathCompletionChar\REG_DWORD

要设置 REG_DWORD 值,请运行 Regedit.exe 并使用特定功能的控制字符的十六进制值(例如,用 0×9 表示 TAB 键,用 0×08 表示 BACKSPACE 键)。用户特定设置优先于计算机设置,并且命令行选项优先于注册表设置。

警告

编辑注册表不当可能会严重损坏您的系统。在更改注册表之前,应备份计算机上任何有价值的数据。

如果使用 /f:on 启用了文件和目录名完成,则对于目录名完成,可使用 CTRL+D 组合键;而对于文件名完成,可使用 CTRL+F 组合键。要禁用注册表中特定字符的完成,请使用空格值 [0×20],因为空格不是有效的控制字符。

按 CTRL+D 或 CTRL+F 组合键时,cmd 会处理文件和目录名的完成操作。这些组合键的作用是在 string 后附加通配符(如果还未使用),并创建匹配的路径列表,然后显示第一个匹配的路径。如果所有路径都不匹配,文件和目录名完成操作会发出警告声,并且不更改所显示的内容。要逐个查看匹配路径列表中的路径,请重复按 CTRL+D 或 CTRL+F 组合键。要向后查看该列表,请在按 SHIFT 的同时按 CTRL+D 或 CTRL+F 组合键。要放弃已保存的匹配路径列表并生成新列表,可以编辑 string,然后按 CTRL+D 或 CTRL+F 组合键。如果在 CTRL+D 和 CTRL+F 组合键之间切换,将会放弃已保存的匹配路径列表并生成新列表。CTRL+D 组合键与 CTRL+F 组合键之间唯一的不同在于,CTRL+D 仅匹配目录名,而 CTRL+F 既匹配文件名,又匹配目录名。如果在任何内部目录命令(CD、MD 或 RD)中使用文件和目录名的完成,将仅使用目录的完成。

如果将匹配路径置于引号之中,则文件和目录名完成会正确地处理含有空格或特殊字符的文件名。

下述特殊字符需要有引号: [ ] { } ^ = ; ! ‘ + , ` ~ [white space]

如果您提供的信息包含空格,请将文本置于引号之中(例如,”Computer Name”)。

如果从 string 中处理文件和目录名完成操作,则位于光标右侧的 [Path] 的任意部分都将放弃(即在 string 中处理完成操作的位置)。

格式化图例

格式 含义

斜体 用户必须提供的信息

粗体 用户必须像显示的一样准确键入的元素

省略号 (…) 可在命令行中重复多次的参数

在括号 ([]) 之间 可选项目

在大括号 ({}) 之间;将选项用竖线 (|) 隔开。例如:{even|odd} 用户必须从中只选择一个选项的选项组

Courier 字体 代码或程序输出

本文来自投稿,不代表【】观点,发布者:【

本文地址: ,如若转载,请注明出处!

举报投诉邮箱:253000106@qq.com

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2024年3月27日 16:14:25
下一篇 2024年3月27日 16:21:32

相关推荐

  • c语言改写模式,c语言实现修改功能

    c语言程序修改? 1、这个程序有4个错误,我都加粗了,第一个是m没有赋初值,第二个是while表达式中的ch=getchar()需要括号括起来,第三个是m=m*10+ch-0中的0也需要用单引号括起来,第四个是第2个while中为m!=0。 2、define容易造成误会,因为不符合一般的编程习惯,false 0, true 1;scanf放在你的那个地方是达…

    2024年5月23日
    4100
  • c语言控制代码的换码序列,c语言交换代码

    求C语言编程大神解答一下下面这个编程代码? k==5,用5去除125余0,所以r=125%5中r为0。由于!0为1,所以执行while循环体:先打印出5(k的值),再n=n/k==125/5=25;由于251则再打印出*号。这一循环结果输出是5*。 下面是我的代码,三个函数分别对应三个问题。 在实现基本要求的前提下,拓展了可以从键盘输入的功能,以下为各题代码…

    2024年5月23日
    5800
  • c语言扫描io脚状态,c语言端口扫描

    求51单片机的上升沿和下降沿C语言检测程序列子,端口就是普通IO口。 上升沿触发是当信号有上升沿时的开关动作,当电位由低变高而触发输出变化的就叫上升沿触发。也就是当测到的信号电位是从低到高也就是上升时就触发,叫做上升沿触发。 单片机怎么计算1s内下降沿的个数的C语言程序或者计算两个下降沿的时间(检测脉冲频率)计算1s内下降沿的个数方法是,一个定时器设置定时1…

    2024年5月23日
    4500
  • c语言mallloc使用的简单介绍

    C语言中使用malloc必须加#includemallo.h? 1、在C语言中使用malloc函数进行动态内存分配。malloc的全称是memory allocation,中文叫动态内存分配。原型:extern void malloc(unsigned int num_bytes);功能:分配长度为num_bytes字节的内存块。 2、你可以看一下C语言那本…

    2024年5月23日
    4500
  • c语言三位小数,C语言三位小数

    怎样用C++语言输出精确到小数点后三位的数? 1、用C++语言输出精确到小数点后三位的数,可以参考下面给出的代码:coutsetiosflags(ios:fixed)setprecision(3)。其中 setiosflags中set是设置的意思。ios是iostream的缩写,即输入输出流。flags是标志的意思。 2、要精确到小数点后若干位,则数据类型为…

    2024年5月23日
    7500
  • c语言21点游戏,二十一点游戏代码c语言

    如何使用C语言编写简单小游戏? 1、数学知识:长方形的面积S=a*b 长方形周长L=2*(a+b)其中a b分别为长方形的宽和高。算法分析:长方形面积及周长均依赖于宽和高,所以先要输入宽高值,然后根据公式计算,输出结果即可。 2、/*也不知道你是什么级别的,我是一个新手,刚接触编程语言,以下是我自己变得一个小程序,在所有c语言的编译器(vc++0、turbo…

    2024年5月23日
    6500
  • c语言当中的null,C语言当中的符号

    C/C++中,NULL和null的区别是什么? nul 和 null要看编译器,不同的编译器有所区别。 所以C或者C++中都使用一个特殊定义NULL表示无效值,其本质就是未定义具体数据类型的0值。 null是是什么都没有的意思。在java中表示空对象。 本意是“空的;元素只有零的”意思。计算机中通常表示空值,无结果,或是空集合。\x0d\x0a在ASCII码…

    2024年5月23日
    4700
  • 包含c语言对txt文件命名的词条

    如何在C语言编程里面修改源文件名字 如果你是在WINDOWS的话,简单了,随便用个编辑器,比如记事本,然后写c源程序,保存到你想要保存的位置。如果你在DOS下,可以用edit,写好以后,按alt键,选择文件菜单,然后保存。 用open打开文件,注意操作模式使用“修改”或者“添加” 用write或者fprintf向文件中写入你的内容。 用close关闭文件。 …

    2024年5月23日
    5000
  • 学c语言编程,学c语言编程用什么软件

    编程开发必须要学C语言吗? 1、要学习。编程开发的学习内容主要包括c语言、python和c+语言。C语言作为一种简单灵活的高级编程语言,它是一个面向过程的语言,一般是作为计算机专业的基础入门语言课程。 2、C语言。对于刚接触编程的人来说,先学习C语言是非常重要的。C语言可以说是是计算机编程语言的鼻祖,其他的编程语言几乎全是由C语言变化衍生出来的。 3、不需要…

    2024年5月23日
    3500
  • c语言用string定义字符串,c语言中用string类型来处理字符串类型

    C++怎样定义定义字符串 1、第一是字符数组来表示字符串。用下面的语句声明:char a[10];C语言中字符数组与字符串的唯一区别是字符串末尾有一个结束符\0,而字符数组不需要。 2、在C中定义字符串有下列几种形式:字符串常量,char数组,char指针 字符串常量 即:位于一对双括号中的任何字符。双引号里的字符加上编译器自动提供的结束标志\0字符,作为 …

    2024年5月23日
    4500

发表回复

登录后才能评论



关注微信