操作系统实验二
实验二 观察Linux行为,使用proc文件系统
一、实验目的
学习Linux内核、进程、存储和其他资源的一些重要特征。读/proc/stat
文件,计算并显示系统CPU占用率和用户态CPU占用率。(编写一个程序使用/proc
机制获得以及修改机器的各种资源参数。需要使用fopen()
,fscanf()
,printf()
)
二、实验内容
Part A
以超级用户的身份进入/proc
目录,在终端上键入ls命令,察看该目录下的内容,同时察看每个文件的读写权限。
选择一台机器,试着回答下列问题:
-
CPU
的类型和型号。 -
所使用的Linux的版本。
-
从启动到当前时刻经过的时间。
-
内存状态。
Part B
-
编写一个程序,用来获得内核参数(任意的参数均可)。
-
编写一个程序,用来修改内核参数(任意的参数均可)。
三、实验步骤
-
使用man命令了解
/proc/stat
文件的内容和格式:man proc
-
使用man命令了解下列函数的使用方法:
fopen:
// 原型如下 FILE *fopen( const char *filename, const char *mode ); // 以打开一个流(文件)。filename——文件名,mode——访问许可类型。
fscanf
// 原型如下 int fscanf( FILE *stream, const char *format [, argument ]); // 从流中读取格式化的数据。
fclose
// 原型如下: int fclose( FILE *stream ); // 关闭流(文件)。
-
用c语言编程
首先编写主函数,建立程序的基本框架,将实现功能的函数放在头文件
info.h
中#include<stdio.h> #include "func.h" // functions inside void extra() { while (1) { printf("Please select from those numbers below:"); printf("\n1:CPU INFO\n2:Linux VERSION INFO\n3:SYSTEM TIME INFO\n4:RAM INFO\n5:sumCpuTime\n"); // some attention info int order = 0; // flag while (order = getchar()) { // printf("%d\n", order); switch (order) { case 49: cpuInfo(); break; case 50: linuxVersion(); break; case 51: sysTime(); break; case 52: ramInfo(); break; case 53: sumCpuTime(); break; } } } } int main(int argc, char *argv[]) { extra(); printf("\nCopy that, over!"); }
对于文件
info.h
定义保存文件的字符数组
shell
以及文件指针ptr
char shell[100]; // the order FILE *ptr = NULL; // file ptr
初始化数组
void initShell() { memset(shell, 0, sizeof(shell)); }
初始化文件指针
void initPtr() { ptr = NULL; }
编写函数
linuxVersion()
显示系统信息/* * To get info about Linux version and print */ void linuxVersion() { ptr = fopen("/proc/version", "r"); // open the source if (ptr == NULL) { printf("Got nothing"); } else { while (1) { if (fgets(shell, 512, ptr) == NULL) { // if the string ended, break break; } printf("Linux version info:%s", shell); // disp the info } fclose(ptr); // close file initPtr(); // init pointer initShell(); // init order array } }
编写函数
cpuInfo()
读取CPU信息/* * To get info about CPU and print */ void cpuInfo() { ptr = fopen("/proc/cpuinfo", "r"); // open the source if (ptr == NULL) { printf("Got nothing"); } else { while (1) { if (fgets(shell, 512, ptr) == NULL) { // if the string ended, break break; } printf("%s", shell); // disp the info } fclose(ptr); initPtr(); initShell(); } }
编写函数
sysTime()
读取系统信息首先定义三个宏保存一天、一小时、一分钟等价秒数(其实按照C的编写要求更应该使用
const int
类型变量)#define DAY 86400 #define HOUR 3600 #define MINUTE 60
函数主体如下
/* * To get info how long the OS' running time */ void sysTime() { int t; // t means time int d, h, m, s; // days, hours, minutes, seconds ptr = fopen("/proc/uptime", "r"); // open the source if (ptr == NULL) { printf("Got nothing"); } else { fscanf(ptr, "%d", &t); // down side here are focusing on format the time we got d = t / DAY; t = t % DAY; h = t / HOUR; t = t % HOUR; m = t / MINUTE; t = t % MINUTE; s = t; printf("Time info:%02ddays:%02dhours:%02dminutes:%02dseconds\n", d, h, m, s); // disp the info } fclose(ptr); initPtr(); }
编写函数
ramInfo()
读取内存信息/* * To get info about ram */ void ramInfo() { ptr = fopen("/proc/meminfo", "r"); // open the source if (ptr == NULL) { printf("Got nothing"); } else { while (1) { if (fgets(shell, 512, ptr) == NULL) { // if the string ended, break break; } printf("Ram info:%s", shell); // disp the info } fclose(ptr); initPtr(); initShell(); } }
编写函数
sumCpuTime()
计算:- 总CPU时间 = 用户占用时间+系统占用时间+优先进程占用时间+闲置进程占用时间
- 系统CPU占用率 = 系统占用时间 / 总CPU时间
- 用户态CPU占用率 = 用户占用时间 / 总CPU时间
void sumCpuTime() { char cpu[10]; long user, nice, sys, idle, iowait, irq, softirq, total; // user_using, sys_using, float sys_usage, user_usage; ptr = fopen("/proc/stat", "r"); if (ptr == NULL) { printf(("Got nothing")); } else { // only the first line will be use fgets(shell, sizeof(shell), ptr); printf("cpu time info:%s\n", shell); sscanf(shell, "%s%ld%ld%ld%ld%ld%ld%ld", cpu, &user, &nice, &sys, &idle, &iowait, &irq, &softirq); total = user + nice + sys + idle + iowait + irq + softirq; // total time sys_usage = (float)sys / (float)total; user_usage = (float)user / (float)total; printf("总时间:%ld", total); printf("系统使用时间占比:%.3f%\n", sys_usage * 100); printf("用户使用时间占比:%.3f%\n", user_usage * 100); } }
info.h
完整结构如下// // Created by lunatic on 2020/10/17. // #include <string.h> #ifndef HOMEWORK2_FUNC_H #define HOMEWORK2_FUNC_H #define DAY 86400 #define HOUR 3600 #define MINUTE 60 char shell[100]; // the order FILE *ptr = NULL; // file ptr void initShell() { memset(shell, 0, sizeof(shell)); } void initPtr() { ptr = NULL; } /* * To get info about Linux version and print */ void linuxVersion() { ptr = fopen("/proc/version", "r"); // open the source if (ptr == NULL) { printf("Got nothing"); } else { while (1) { if (fgets(shell, 512, ptr) == NULL) { // if the string ended, break break; } printf("Linux version info:%s", shell); // disp the info } fclose(ptr); // close file initPtr(); // init pointer initShell(); // init order array } } /* * To get info about CPU and print */ void cpuInfo() { ptr = fopen("/proc/cpuinfo", "r"); // open the source if (ptr == NULL) { printf("Got nothing"); } else { while (1) { if (fgets(shell, 512, ptr) == NULL) { // if the string ended, break break; } printf("%s", shell); // disp the info } fclose(ptr); initPtr(); initShell(); } } /* * To get info how long the OS' running time */ void sysTime() { int t; // t means time int d, h, m, s; // days, hours, minutes, seconds ptr = fopen("/proc/uptime", "r"); // open the source if (ptr == NULL) { printf("Got nothing"); } else { fscanf(ptr, "%d", &t); // down side here are focusing on format the time we got d = t / DAY; t = t % DAY; h = t / HOUR; t = t % HOUR; m = t / MINUTE; t = t % MINUTE; s = t; printf("Time info:%02ddays:%02dhours:%02dminutes:%02dseconds\n", d, h, m, s); // disp the info } fclose(ptr); initPtr(); } /* * To get info about ram */ void ramInfo() { ptr = fopen("/proc/meminfo", "r"); // open the source if (ptr == NULL) { printf("Got nothing"); } else { while (1) { if (fgets(shell, 512, ptr) == NULL) { // if the string ended, break break; } printf("Ram info:%s", shell); // disp the info } fclose(ptr); initPtr(); initShell(); } } void sumCpuTime() { char cpu[10]; long user, nice, sys, idle, iowait, irq, softirq, total; // user_using, sys_using, float sys_usage, user_usage; ptr = fopen("/proc/stat", "r"); if (ptr == NULL) { printf(("Got nothing")); } else { // only the first line will be use fgets(shell, sizeof(shell), ptr); printf("cpu time info:%s\n", shell); sscanf(shell, "%s%ld%ld%ld%ld%ld%ld%ld", cpu, &user, &nice, &sys, &idle, &iowait, &irq, &softirq); total = user + nice + sys + idle + iowait + irq + softirq; // total time sys_usage = (float)sys / (float)total; user_usage = (float)user / (float)total; printf("total time:%ld", total); printf("percentage of system time:%f%\n", sys_usage * 100); printf("percentage of user time:%f%\n", user_usage * 100); } } #endif //HOMEWORK2_FUNC_H
编写程序,实现一次性查看
/proc
下的多个文件// // Created by Lunatic on 2020/11/25. // #include <stdio.h> int main(int argc, char *argv[]) { char buffer[100]; FILE *fp; int i = 1; for (; 1; i++) { if (argc[1] == NULL) { printf("There's no file out there"); return 0; } fp = fopen(argv[1], "r"); if (fp == NULL) { printf("File could not be opened\n"); } else { while (1) { if (fgets(buffer, 100, fp) == NULL) { break; } printf("%s", buffer); } fclose(fp); } } return 0; }
四、实现结果
使用如下命令进行编译,输出一个名为task
的二进制文件
gcc -o task main.c
开始执行
依次测试各功能:
-
CPU INFO
查看CPU信息 -
Linux VERSION INFO
查看Linux
版本信息 -
SYSTEM INFO
查看本机操作系统系统信息 -
RAM INFO
查看内存信息 -
sumCpuTime
查看占用事件 -
输入命令读取多个文件
执行程序,在之后附上命令,查看
Linux
版本信息./a1 /proc/version /proc/cpuinfo
五、实验心得
本次实验学习了在Linux
如何使用Vim
编写程序以及如何调用编译器对编写的程序进行编译。Linux
的文件均存放在/proc
目录下,在用户态下进行编程,使用文件指针读取文件即可查看相关的文件信息。
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。 如若内容造成侵权/违法违规/事实不符,请联系我的编程经验分享网邮箱:veading@qq.com进行投诉反馈,一经查实,立即删除!