当前位置: 首页 > news >正文

岳阳网站开发公司推荐手机访问跳转手机网站

岳阳网站开发公司推荐,手机访问跳转手机网站,海南做网站电话,沧州网络公司电话操作系统系列#xff1a;关于终端 Shell在Win32上创建一个新进程重定向输入和输出 Shell Unix命令处理器或者Shell都是进程#xff0c;它获取用户键入的命令#xff0c;fork出一个进程#xff0c;子进程调用exec来执行用户的命令#xff0c;父进程等待子进程执行结束。 这… 操作系统系列关于终端 Shell在Win32上创建一个新进程重定向输入和输出 Shell Unix命令处理器或者Shell都是进程它获取用户键入的命令fork出一个进程子进程调用exec来执行用户的命令父进程等待子进程执行结束。 这是一段简单的shell伪代码 pid_t pid;while (1) {GetNextCommand();pid fork();if (pid 0) {ExecCommand();PrintErrorMsg()exit(0);}else if (pid 0) wait();else HandleForkFailure();}Unix 允许用户通过在命令行中添加与号 () 来实现在后台运行命令当进程在后台运行时他不能从终端接收用户输入并立即显示 shell 提示符允许用户在后台进程完成之前输入新命令。对于上面的伪代码如果想要在后台运行开发者要做些什么呢 在Win32上创建一个新进程 这是在Win32上创建新进程的API BOOL CreateProcess( LPCTSTR lpApplicationName, /* executable program */LPTSTR lpCommandLine, /* command line args */LPSECURITY_ATTRIBUTES lpProcessAttributes, /* use NULL */LPSECURITY_ATTRIBUTES lpThreadAttributes, /* use NULL */BOOL bInheritHandles, /* does proc inherit parents open handles */DWORD dwCreationFlags, LPVOID lpEnvironment, /* if NULL, use parent environment */LPCTSTR lpCurrentDirectory, /* if NULL, use parent curr dir */LPSTARTUPINFO lpStartupInfo, LPPROCESS_INFORMATION lpProcessInformation ); typedef struct PROCESS_INFORMATION {HANDLE hProcess;HANDLE hThread;DWORD dwProcessId;DWORD dwThreadId; } PROCESS_INFORMATION;CreateProcess相当于Unix上的fork()和exec()。相比于Unix的系统调用Win32 APIs几乎都会有很多的参数。 LPCTSTR lpApplicationName 这是要执行的进程的路径名相当于 Unix execl 命令的第一个参数它可以是相对路径名或绝对路径名。LPTSTR lpCommandLine 这个参数通常是 NULLLPSECURITY_ATTRIBUTES lpProcessAttributes 进程属性通常是NULLLPSECURITY_ATTRIBUTES lpThreadAttributes 线程属性通常是NULLBOOL bInheritHandles 如果该值为 TRUE则每表示个打开的文件句柄或其他句柄也可以在子进程中打开DWORD dwCreationFlags 通过该值设置一些标志默认值是0LPVOID lpEnvironment 允许开发者改变环境如果该值取NULL表示子进程继承父进程的环境LPCTSTR lpCurrentDirectory 允许开发者改变目录如果为 NULL则子进程与父进程有相同的当前工作目录LPSTARTUPINFO lpStartupInfo 这是一个指向有关如何呈现新进程的信息的指针。 在Windows环境中一个新进程通常是一个新窗口它会告诉操作系统该窗口放置在哪里窗口的高度和宽度以及其他信息。LPPROCESS_INFORMATION lpProcessInformation 这是一个向父级返回有关子级的信息的结构例如进程 ID 和句柄。 与大多数 Win32 API 一样此调用在成功时返回 TRUE在失败时返回 FALSE。 下面是一段简短的示例代码用于启动记事本。 #include windows.h #include stdio.h #include string.hchar *GetErrorMessage() {char *ErrMsg;FormatMessage( FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,NULL,GetLastError(),MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), // Default language(LPTSTR) ErrMsg,0,NULL );return ErrMsg; }int main() {char commandline[255];PROCESS_INFORMATION ProcessInfo;STARTUPINFO StartupInfo;strcpy(commandline,notepad);GetStartupInfo(StartupInfo);if (CreateProcess (c:\\winnt\\notepad.exe,commandline, NULL, NULL,FALSE, 0, NULL, NULL, StartupInfo,ProcessInfo) TRUE) {printf(Create was successful\n);printf(Proc id is %d\n,ProcessInfo.dwProcessId);}else {printf(error, CreateProcess failed, error number %d\n,GetLastError());printf(%s\n,GetErrorMessage());}return 0; }请特别注意 CreateProcess 的第一个参数由于反斜杠是字符串中的转义字符因此字符串中的反斜杠字符必须用双反斜杠表示。 这在 Unix 中不会出现太多但在 Windows 中却是个一直存在的问题因为反斜杠是目录分隔符。 重定向输入和输出 不管在 Unix上还是在Windows 上当创建一个新进程时都会自动创建三个 I/O 流它们称之为标准输入、标准输出和标准错误。 标准输入默认为控制终端的键盘标准输出和标准错误默认为控制终端的监视器。 监视器默认有两个单独的输出流的原因是有时用户希望将正常输出重定向到文件但希望将错误消息显示在终端上或发送到 不同的文件。 用户可以在 shell 提示符下使用 运算符将进程的输出从终端重定向到文件。 例如 ls -l outfile这个操作会将 ls -l 命令的输出发送到名为 outfile 的文件而不是终端。 shell 还可以将标准输入从键盘重定向到带有 字符的文件。 每个 Unix 进程都有一个与其关联的文件描述符数组。系统调用 open 就返回一个文件描述符文件描述符是一个低位正整数。 按照约定标准输入是文件描述符 0标准输出是文件描述符 1标准错误是文件描述符 2。 当程序打开文件时通常会为其分配最低的未使用文件描述符。写入到终端的函数例如 printf或者从键盘读取的函数例如 scanf、getchar都会调用写入和读取系统调用并将文件描述符设置为标准输出和标准输入。 如果开发者想要将标准输入或标准输出从程序内重定向到文件请使用 dup 或 dup2 系统调用。 这两个调用会复制一个文件描述符对 dup2 的调用需要两个参数fd1 和 fd2它们都是文件描述符。 第一个参数 fd1 必须是已打开的文件描述符 该调用使 fd2 引用与 fd1 相同的文件。 如果fd2打开则首先要把它关闭。 请看下面的例子 /* dup2.c - a demo of the dup2 call */ #include stdio.h #include fcntl.h #include errno.h #include unistd.h int main() {int fd, retval;fd open(temp,O_WRONLY | O_CREAT | O_TRUNC, 0200 | 0400); /* fd is probably 3, the lowest unused file descriptor */if (fd 0) {perror(Error on opening temp);exit(0);}printf(This line written on the terminal\n);retval dup2(fd,1); if (retval ! 1) {perror(Error on dup2);exit(0);} printf(This line is written to the file temp\n);return 0; }该程序打开一个名为 temp 的文件进行写入然后它调用 printf将一行写入终端下一行是程序的关键语句 retval dup2(fd, 1);该行使文件描述符 1 引用 fd 引用的文件由于文件描述符 1 引用标准输出因此首先要将其关闭。 在 printf 函数中有一行代码如下所示 n write(1,.....通常文件描述符1指的是标准输出但我们的程序重新定义了它使其指的是文件temp因此对 write 的调用将写入文件而不是终端。如果成功dup2 返回其第二个参数的值否则返回负值。 dup 是 dup2 的老版本它只使用一个参数即要复制的文件描述符并将最低的未使用文件描述符设置为等效。 要使用此功能请在调用 dup 之前根据需要关闭文件描述符 0 或 1。 请参见dup2的帮助文档。 NAME dup2 - 复制打开的文件描述符SYNOPSIS #include unistd.h int dup2(int fildes, int fildes2);DESCRIPTION dup2() 函数使文件描述符 fildes2 引用与 fildes 相同的文件。 fildes 参数是引用打开文件的文件描述符fildes2 是一个非负整数小于调用进程允许的打开文件描述符最大数量的当前值。 请参阅 getrlimit(2)。 如果 fildes2 已经引用了一个打开的文件而不是 fildes则首先将其关闭。 如果fildes2引用fildes或者fildes不是有效的打开文件描述符则fildes2不会首先被关闭。dup2() 函数相当于 fcntl(fildes, F_DUP2FD, fildes2).RETURN VALUES 成功完成后将返回表示文件描述符的非负整数。 否则返回-1并设置errno以指示错误。ERRORSEBADF - fildes参数不是有效的打开文件描述符。.EBADF - files2参数为负数或不小于 getrlimit(RLIMIT_NOFILE, …) 返回的当前资源限制。EINTR - 在调用dup2时返回了一个信号。EMFILE - 进程打开了过多的文件。 调用 fork 后会创建一个与旧进程相同的新进程父进程的文件描述符表也会复制到子进程因此如果父进程有一个打开的文件子进程将继承这个打开的文件。 此外如果父进程复制了文件描述符子进程也将继承它文件描述符表也会通过对系统调用 exec 系列成员的调用进行复制。 这对于 shell 的实现很重要shell 分叉出一个新进程来执行命令如果用户指定输出到文件而不是标准输出那么shell 可以使用 dup2 来将标准输出重定向到文件然后再调用 exec 来执行命令。 祭出一个编程小作业 请编写一个简单的 shell它在一个无限循环中重复执行以下操作 显示提示 ()从用户处获取命令行解析命令行执行命令 用户输入的命令行应包含一个命令该命令可以是相对路径名或绝对路径名后跟零个或多个参数然后是输入和输出重定向。 stdin 或 stdout 都可以重定向或者两者都不能重定向。 如果用户附加一个与号 ()则该进程应在后台运行。 以下都是有效的命令行 a.out a.out arg1 arg2 a.out arg1 arg2 outfile infile a.out arg1 arg2outfile 这个作业最难的部分是解析命令行您可以下载一个文件 ParseCommandLine.h它定义了一个 CommandData 结构体包含执行命令所需的命令行中的所有数据。 struct CommandData {char *command; /* the pathname of the command */char *args[11]; /* arguments to the command */int numargs; /* the number of arguments */char *infile; /* the file for input redirection, NULL if none */char *outfile; /* the file for output redirection, NULL if none */int background; /* 0 if process is to run in foreground, 1 if in background */ };它还定义了一个函数 int ParseCommandLine(char *line, struct CommandData *data)它接受两个参数即用户输入的命令行以及指向 CommandData 结构的指针其内存必须由调用函数分配。 该函数解析命令行并填充 CommandData 结构: 如果没有错误则返回 1如果用户输入无效命令则返回 0。 在后一种情况下数据的内容是不确定的。 某些对于真实 shell 具有特殊含义的字符不能与此 shell 一起使用。 命令名和路径名只能使用以下字符大写或小写字母、数字、下划线、斜杠、连字符或点。、 和 字符具有特殊含义不能在文件名中使用。任何其他字符例如美元符号、星号、问号、引号、逗号、管道、双引号或波形符都将在 ParseCommandLine 函数中生成错误条件。文件名和路径名的名称中不能有空格。 如果命令是 quit 你的程序应该终止。 您的 shell 应该执行该命令根据需要重定向 stdin 和 stdout并将参数传递给程序。 请注意按照约定因此对于此分配argv[0] 是实际命令您必须填写此命令。 如果命令行是: a.out arg1 arg2 infile outfile当a.out启动时argv[0]的值应该是a.outargv[1]的值应该是arg1argv[2]的值应该是arg2。 您的 shell 不需要搜索路径所有相对路径名都应从当前工作目录开始。 请注意这意味着如果命令行是 ls您的程序将回复 command not find除非当前目录中碰巧存在名为 ls 的可执行文件要运行 ls用户必须输入 /bin/ls 并注意您的 shell 必须将 argv[0] 设置为 ls。
http://www.zqtcl.cn/news/303685/

相关文章:

  • 杭州网站优化公司哈尔滨企业网站模板建站
  • 洛阳免费网站建设自己做网站最新视频教程
  • 网站备案查询 美橙网开发app需要的技术
  • 软件产品如何做网站推广昆山外贸网站建设推广
  • 景德镇市城市建设规划网站wordpress用不了了
  • 网站及新媒体建设宣传片wordpress 无法编辑主题
  • 东莞设计网站重庆做腋臭骑士网站
  • 什么软件可以搜索关键词精准网站信息优化的方式
  • 购物网站排名前十名山东泰安建筑工程集团有限公司
  • 源码下载站用vs网站开发
  • 自己做网站seo彩票的网站怎么做
  • 如何在网站后台找到死链接网站内页权重查询
  • 专业做国际网站网站开发的编程软件
  • 如何运营垂直网站网页工具大全
  • 如何让自己做的网站可以播放歌曲做培训网站
  • 做网站的毕业设计网站没备案怎么做淘宝客
  • 百度申诉网站建设银行住房租赁代表品牌是什么
  • 网站初期推广方案虚拟服务器搭建wordpress
  • jeecms可以做网站卖吗山西网络推广专业
  • 2017 如何做网站优化育儿哪个网站做的好
  • 网站制作容易吗青岛网站建设公司报价
  • 淘宝建设网站的好处网站制作结构
  • 网站开发网站建设公司临沂网站建设找谁
  • 咋么做网站在电脑上潍坊免费模板建站
  • 苏州网站建设推广咨询平台做网站的公司图
  • 北京企业网站怎么建设免费给我推广
  • 网站制作价钱多少专业的咨询行业网站制作
  • 做百度网站每年的费用多少交换友情链接时需要注意的事项
  • 怎么在百度网站上做自己的网站百度开户渠道
  • php技术的网站建设实录方案做二手手机的网站有哪些