Linux Day10 ---Mybash
目录
一、Mybash介绍
1.1.mybash.c
打印函数
分割函数
命令函数
二、Mybash实现
2.1.打印函数
2.1.1需要使用到的功能函数
1.获取与当前用户关联的UID
2.获取与当前用户的相关信息---一个结构体(passwd)
3.获取主机信息
4.获取当前所处位置
5.给对应字体加颜色
2.1.2 打印函数实现
2.2 分割函数
2.2.1 strtok函数
2.2.2分割函数实现
2.3 命令函数
2.3.1 exit
2.3.2 clear
2.3.3 cd
2.3.4 chmod
2.3.5 pwd
2.3.6 mkdir
2.3.7 rmdir
2.3.8 rm
2.3.9 复制、更新进程
三、使用看效果
一、Mybash介绍
1.1.mybash.c
这个函数用来实现mybash,可分为三大部分:打印函数、分割函数、命令函数
打印函数
打印出如下的功能

能够和bash一样显示出用户+主机名+当前目录+用户身份
分割函数
将输入的命令按空格分割,并保存到相应的数组中,使用到strtok()字符分割函数。
命令函数
根据exec系列学习,采用fork+exec,父进程等待,子进程采用exec,调用自己实现的命令文件,进行真实命令的模拟
二、Mybash实现
2.1.打印函数
2.1.1需要使用到的功能函数
1.获取与当前用户关联的UID
uid_t getuid(void);
如果得到是0,就是管理员,初始为普通用户。
2.获取与当前用户的相关信息---一个结构体(passwd)
passwd成员 说明
char* pw_name 用户登录号
uid_t pw_uid UID号
gid_t pw_gid GID号
char* pw_dir 用户家目录
char* pw_gecos 用户全名
char* pw_shell 用户默认shell
struct passwd*getwuid(uid_t uid);
这里可以定义一个相对应类型的指针ptr去指向该结构体,进而->方式访问到该用户的UID号
3.获取主机信息
int gethostname(char*name,size_t namelen);
gethostname函数把机器的主机名写入到name字符串里,该字符串至少有namelen个字符长。而成功,gethostname的返回0,否则返回-1。
4.获取当前所处位置
char*getcwd(char*buf,size_t size);
getcwd函数把当前目录的名字写入给定的缓冲区-buf,如果目录名长度超出参数size给出的缓冲区长度,就返回NULL,如果成功,返回指针buf。
5.给对应字体加颜色
详细参考printf函数中的/033一系列。
2.1.2 打印函数实现
void print_info()
{uid_t uid=getuid();char*s="$";if(uid==0){s="#";}struct passwd* ptr=getpwuid(uid);if(ptr==NULL){printf("mybash 1.0 $");fflush(stdout);return;}char hostname[128]={0};if(gethostname(hostname,128)==-1){printf("mybash 1.0 $");fflush(stdout);return;}char curr_dir[256]={0};if(getcwd(curr_dir,256)==NULL){printf("mybash 1.0 $");fflush(stdout);return;}printf("\033[1;32m%s@%s\033[0m\033[1;34m:%s\033[0m %s ",ptr->pw_name,hostname,curr_dir,s);fflush(stdout);return;
}
2.2 分割函数
2.2.1 strtok函数
char* strtok(char*str,const char*delim);
str为需要分割的字符串,delim为分割标记。
通常需要循环使用,如果需要多次分割当前字符串,在第二次使用的时候字符串那使用NULL,系统会认为继续对当前字符串进行分割(这里有个指针会指向第一次分割完后的位置)。
2.2.2分割函数实现
char* get_cmd(char buff[],char*myargv[])
{if(buff==NULL||myargv ==NULL){return NULL;}int i=0;char*s=strtok(buff," ");while(s!=NULL){myargv[i++]=s;s=strtok(NULL," ");}return myargv[0];
}
2.3 命令函数
2.3.1 exit
exit表示退出当前进程。
if(strcmp(cmd,exit)==0){break;}
2.3.2 clear
clear表示清屏,并将光标放置在最上方最左边位置

\033[2J 清屏
\033[y;xH设置光标位置
if(strcmp(cmd,"clear")==0){printf("/033[2J]\033[0;0H");}
2.3.3 cd
首先先说下myargv就是argv,在前面的文里说过int main(int argc,char*argv[],char*envp[]),这里的myargv里面就存储了需要切换到的路径。
其次,程序可以像用户在文件系统里那样来切换目录,就像在shell里面使用cd命令来切换目录一样。程序使用的是chdir系统调用。
int chdir(const char*path);
这里的path存储在myargv[1]里面,myargv[0]为命令cd .
成功返回0,失败返回-1
if(strcmp(cmd,"cd")==0){if(myargv[1]!=NULL){if(chdir(myargv[1])==-1){perror("cd err\n");}}continue;}
2.3.4 chmod
首先先来看看shell里面的chmod

第一个参数为权限设置,第二个参数为需要修改的文件
所以我们通过查看书,可以发现chmod的系统调用
int chmod(const char*path,mode_t mode);
path参数指定的文件被修改为具有mode参数给出的访问权限。
注意我们这里的参数为8进制,所以涉及到参数进制转换。
if(strcmp(cmd,"chmod")==0){const char*path=myargv[2];int mode=atoi(myargv[1]);int mode_1=mode/10/10;int mode_3=mode%10;int mode_2=mode/10%10;mode=mode_1*8*8+mode_2*8+mode_3;if(chmod(path,mode)<0){printf("chmod err\n");}continue;}
2.3.5 pwd
getcwd在上面的打印函数中提过,详细请参考上面。
if(strcmp(cmd,"pwd")==0){char cwd[128]={0};if(getcwd(cwd,128)==NULL){printf("pwd err\n");continue;}printf("%s\n",cwd);continue;}
2.3.6 mkdir
mkdir系统调用用于创建目录,他相当于mkdir程序。mkdir调用将参数path作为新建目录的名字。目录的权限由参数mode设定,将含义按open系统调用的O_CREAT选项的有关定义设置。
int mkdir(const char* path,mode_t mode);
注意mode数值的设定。
if(strcmp(cmd,"mkdir")==0){char* path=myargv[1];mode_t mode=7*8*8+7*8+5;if(mkdir(path,mode)==-1){printf("mkdir err\n");}continue;}
2.3.7 rmdir
rmdir系统调用用于删除目录,但只有在目录为空才行,rmdir程序就是用这个系统调用来完成工作的。
int rmdir(const char*path);
if(strcmp(cmd,"rmdir")==0){char*path=myargv[1];DIR* dir = opendir("path");if(dir == NULL){perror("打开目录失败");exit(1);}struct dirent *ptr = NULL;while((ptr=readdir(dir))!=NULL);if(ptr == NULL){rmdir(myargv[1]);}continue;}
这里我先通过调用opendir和readdir两个函数来判断当前目录是否为空,进而使用rmdir函数来删除当前目录。
opendir函数的作用是打开一个目录并建立一个目录流,成功返回一个指向DIR结构的指针,该指针用于读取目录数据项,失败则返回一个空指针。
DIR*opendir(const char*name);
然后继续使用readdir()函数,返回一个指针,该指针指向结构里面保存着目录流dirp中下一个目录项的有关资源,后续的readdir调用返回后续的目录项,如果错误或者到达目录尾则返回NULL。
因此使用了while循环。
2.3.8 rm
rm可以直接删除普通目录文件,但是不能直接删除普通文件,需要使用到rm -r
因此这里我们需要获取到当前文件的类型
文件的类型存储在struct stat

if(strcmp(cmd,"rm")==0){char*path1=myargv[1];char*path2=myargv[2];struct stat buf;char * ptr;int result;result = stat(myargv[3], &buf);if(S_ISREG(buf.st_mode)){if(strcmp(cmd,strcat(path1,path2))==0){unlink(myargv[3]);}}if(S_ISDIR(buf.st_mode)){rmdir(myargv[3]);}}
如果是普通文件,我们使用unlink系统调用删除一个文件。
unlink系统删除一个文件的目录项并减少他的链接数,它成功返回0失败返回-1.
如果想通过这个函数成功删除文件,你就必须拥有该文件所属目录的写和执行权限。
2.3.9 复制、更新进程
pid_t pid=fork();if(pid==-1){printf("fork err\n");continue;}if(pid==0){execvp(cmd,myargv);printf("exec err\n");exit(0);}wait(NULL);
剩余命令我们后续更新。。。。敬请期待
接下来我们看一下效果
三、使用看效果

下次我们更新touch ,mv,cp,ls,cat等命令
相关文章:
Linux Day10 ---Mybash
目录 一、Mybash介绍 1.1.mybash.c 打印函数 分割函数 命令函数 二、Mybash实现 2.1.打印函数 2.1.1需要使用到的功能函数 1.获取与当前用户关联的UID 2.获取与当前用户的相关信息---一个结构体(passwd) 3.获取主机信息 4.获取当前所处位置 5.给…...
Flask-Sockets和Flask-Login联合实现websocket的登录认证功能
flask_login 提供了一个方便的方式来管理用户会话。当你在 Flask 的 HTTP 视图中使用它时,你可以简单地使用 login_required 装饰器来确保用户已登录。 但是,flask_sockets 并没有直接与 flask_login 集成。如果你想在建立 WebSocket 连接时检查用户是否…...
东盟全面覆盖?长城战略部署核心区域市场,首个百万粉丝国产品牌
根据最新消息,长城汽车在东南亚地区取得了巨大的成功,成功进军了亚洲最大的汽车市场之一-印度尼西亚。这标志着长城汽车已经实现了东盟核心市场的全面覆盖,成为全球布局的重要一步。 在过去的几年里,长城汽车在东盟地区的市场布局…...
基于PHP的电脑商城系统
有需要请加文章底部Q哦 可远程调试 基于PHP的电脑商城系统 一 介绍 此电脑商城系统基于原生PHP开发,数据库mysql,前端bootstrap。用户可注册登录,购物下单,评论等。管理员登录后台对电脑商品,用户,订单&a…...
无客户端网络准入方案,为集成电路企业终端管理开启省事更省心模式
宁盾无客户端网络准入控制方案正在成为先进制造、高科技互联网企业等创新型客户的优选方案。创新型客户以技术密集型、研发人员占比高著称,在进行网络准入建设时,如何平衡好用户体验与顺利达成项目预期之间的矛盾,是创新企业 IT 安全团队格外…...
5G与4G的RRC协议之异同
什么是无线资源控制(RRC)? 我们知道,在移动通信中,无线资源管理是非常重要的一个环节,首先介绍一下什么是无线资源控制(RRC)。 手机和网络通过无线信道相互通信,彼此交…...
横扫“盲区”、“看透”缺陷,维视智造推出短波红外相机
在可见光领域,工业相机的视觉应用已经十分成熟,但在日常的客户咨询中,我们也经常接到一些“超纲需求”——客户想要检测“白底上的白色缺陷”、“不透明包装内的透明物体有无”等,均属于可见光无法实现的检测,而市面上…...
cgo踩坑:交叉编译过程出现的问题could not determine kind of name for C.XXX
尝试了网上的几种解决方法,都不行,现总结起来: 确认 /* #include <stdio.h> */ import "C"不要有空行 确认你引用的头文件存在(stdio.h这种编译器自带的不需要你确认) 如果引用了多个包,…...
自然语言处理(NLP)技术的例子
以下是几个自然语言处理(NLP)技术的例子: 机器翻译:机器翻译是将一种自然语言的文本转换成另一种语言的文本的过程。这种技术应用于在线翻译器、多语言聊天机器人、多语言搜索引擎等地方。 文本分类:文本分类将文本分…...
Python“牵手”义乌购商品列表数据,关键词搜索义乌购API接口数据,义乌购API接口申请指南
义乌购平台API接口是为开发电商类应用程序而设计的一套完整的、跨浏览器、跨平台的接口规范,义乌购API接口是指通过编程的方式,让开发者能够通过HTTP协议直接访问义乌购平台的数据,包括商品信息、店铺信息、物流信息等,从而实现义…...
ip_vs 原理解析 (四)hook 后的开始 NF_INET_LOCAL_IN
文章目录 ip_vs hook 后NF_INET_LOCAL_IN 本章重点: k8s 如何利用 ip_vs 实现源 IP 会话亲和性。 ip_vs hook 后 NF_INET_LOCAL_IN 根据优先级依次是 ip_vs_reply4,ip_vs_remote_request4 ip_vs_reply4| -- ip_vs_out| -- skb_to_full_sk(skb…...
分布式之CAP理论与BASE理论
CAP理论 CAP:一致性(consistency)、可用性(Availability)、分区容错(partition-tolerance)。CAP定律说的是在一个分布式计算机系统中,一致性,可用性和分区容错性这三种保证无法同时…...
Java之初始化顺序实践
功能概述 在创建Java对象时,需要将对象中的成员变量进行初始化后,才能调用对象的构造方法创建对象。本文中将会讲解初始化时父类与子类对应的顺序。 功能实践 场景1:父类、子类的初始化顺序 用例代码 Test public void test_init_order(…...
静态库与动态链接库,第三方库集成到VS
目录 介绍静态库与动态链接库静态库动态链接库 如何将第三方库集成到VS上VS属性管理器配置静态库配置动态链接库属性管理器其他的内容MKL库的安装boost库的安装 介绍 众所周知,.c文件或者.cpp文件变成.exe文件需要经历四个过程 分别是预处理,编译&#…...
生态经济学领域里的R语言机器学(数据的收集与清洗、综合建模评价、数据的分析与可视化、数据的空间效应、因果推断等)
近年来,人工智能领域已经取得突破性进展,对经济社会各个领域都产生了重大影响,结合了统计学、数据科学和计算机科学的机器学习是人工智能的主流方向之一,目前也在飞快的融入计量经济学研究。表面上机器学习通常使用大数据…...
【ROS】自定义消息方面的bug总结(1)
根据需要创建功能包 一类引用ros库函数的一类是自己定义的消息类型 库函数中有的可以直接在创建功能包的时候添加依赖,也可以在CMakeLists.txt中手动添加 catkin_create_pkg crepes roscpp rospy std_msgs nav_msgs sensor_msgs geometry_msgs创建文件夹msg…...
CTF-XXE(持续更新,欢迎分享更多相关知识点的题目)
知识 实例 BUU [PHP]XXE 进来看到 然后一起看 Write BUU XXE COURSE 1 进来看到 一起看 write NSS [NCTF2019]Fake XML cookbook 反正是XXE 直接整 write [NCTF 2019]True XML cookbook 不整花里胡哨,解题在最下面 write 与博主不同,我通过…...
Python工具箱系列(四十一)
使用zip批量压缩文件 前文的代码示例了使用gzip对单个文件进行压缩。本文示例使用更通用的zipfile来批量压缩文件。zipfile也是python内置的库,使用起来非常方便。废话不说,直接上代码示例。 import dbm import glob import zipfile# 保存压缩计划的库名…...
Bigemap在路桥行业是怎么应用的?
选择Bigemap的原因: 奥维下架了,后来了解到的bigemap,于是测试了这款软件 使用场景: 下载影像、矢量路网做前期策划,下载完数据后导出cad ,做一些标注,最终出图下载等高线,作为前期选址依据 …...
代码随想录算法训练营Day48 || ● 198.打家劫舍 ● 213.打家劫舍II ● 337.打家劫舍III
问题1:198. 打家劫舍 - 力扣(LeetCode) 你是一个专业的小偷,计划偷窃沿街的房屋。每间房内都藏有一定的现金,影响你偷窃的唯一制约因素就是相邻的房屋装有相互连通的防盗系统,如果两间相邻的房屋在同一晚上…...
龙虎榜——20250610
上证指数放量收阴线,个股多数下跌,盘中受消息影响大幅波动。 深证指数放量收阴线形成顶分型,指数短线有调整的需求,大概需要一两天。 2025年6月10日龙虎榜行业方向分析 1. 金融科技 代表标的:御银股份、雄帝科技 驱动…...
日语学习-日语知识点小记-构建基础-JLPT-N4阶段(33):にする
日语学习-日语知识点小记-构建基础-JLPT-N4阶段(33):にする 1、前言(1)情况说明(2)工程师的信仰2、知识点(1) にする1,接续:名词+にする2,接续:疑问词+にする3,(A)は(B)にする。(2)復習:(1)复习句子(2)ために & ように(3)そう(4)にする3、…...
css的定位(position)详解:相对定位 绝对定位 固定定位
在 CSS 中,元素的定位通过 position 属性控制,共有 5 种定位模式:static(静态定位)、relative(相对定位)、absolute(绝对定位)、fixed(固定定位)和…...
前端开发面试题总结-JavaScript篇(一)
文章目录 JavaScript高频问答一、作用域与闭包1.什么是闭包(Closure)?闭包有什么应用场景和潜在问题?2.解释 JavaScript 的作用域链(Scope Chain) 二、原型与继承3.原型链是什么?如何实现继承&a…...
算法:模拟
1.替换所有的问号 1576. 替换所有的问号 - 力扣(LeetCode) 遍历字符串:通过外层循环逐一检查每个字符。遇到 ? 时处理: 内层循环遍历小写字母(a 到 z)。对每个字母检查是否满足: 与…...
渗透实战PortSwigger靶场:lab13存储型DOM XSS详解
进来是需要留言的,先用做简单的 html 标签测试 发现面的</h1>不见了 数据包中找到了一个loadCommentsWithVulnerableEscapeHtml.js 他是把用户输入的<>进行 html 编码,输入的<>当成字符串处理回显到页面中,看来只是把用户输…...
GraphRAG优化新思路-开源的ROGRAG框架
目前的如微软开源的GraphRAG的工作流程都较为复杂,难以孤立地评估各个组件的贡献,传统的检索方法在处理复杂推理任务时可能不够有效,特别是在需要理解实体间关系或多跳知识的情况下。先说结论,看完后感觉这个框架性能上不会比Grap…...
StarRocks 全面向量化执行引擎深度解析
StarRocks 全面向量化执行引擎深度解析 StarRocks 的向量化执行引擎是其高性能的核心设计,相比传统行式处理引擎(如MySQL),性能可提升 5-10倍。以下是分层拆解: 1. 向量化 vs 传统行式处理 维度行式处理向量化处理数…...
python读取SQLite表个并生成pdf文件
代码用于创建含50列的SQLite数据库并插入500行随机浮点数据,随后读取数据,通过ReportLab生成横向PDF表格,包含格式化(两位小数)及表头、网格线等美观样式。 # 导入所需库 import sqlite3 # 用于操作…...
npm安装electron下载太慢,导致报错
npm安装electron下载太慢,导致报错 背景 想学习electron框架做个桌面应用,卡在了安装依赖(无语了)。。。一开始以为node版本或者npm版本太低问题,调整版本后还是报错。偶尔执行install命令后,可以开始下载…...
