C++代码: Linux下获取基本设备信息

测试环境

基于C++20构建测试 (g++ 10.2.1)
在这里插入图片描述

CMakeLists.txt

# 设置用于构建该项目的最低cmake版本
cmake_minimum_required(VERSION 3.1)

# 设置项目名称和编程语言
project(获取Linux信息 CXX)

# 设置二进制文件生成路径
set(EXECUTABLE_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/bin)
# 获取源码的路径
aux_source_directory(src src)

# 设置编译标准和额外参数
add_compile_options(-std=c++20 -Wall -Werror -Wextra -pedantic -Wimplicit-fallthrough -Wsequence-point -Wswitch-default -Wswitch-unreachable -Wswitch-enum -Wstringop-truncation -Wbool-compare -Wtautological-compare -Wfloat-equal -Wshadow=global -Wpointer-arith -Wpointer-compare -Wcast-align -Wcast-qual -Wwrite-strings -Wdangling-else -Wlogical-op -Wconversion -Wno-pedantic-ms-format)

# 从源码构建二进制文件
add_executable(demo ${src})

结构参考下图
在这里插入图片描述

源码

1.获取IP

/**
 * @file getIP.cpp
 * @author IYATT-yx
 * @brief 获取IP
 * @details Ubuntu 20.04 64-bit  C++20
 */
#include <iostream>
#include <cstring>

extern "C"
{
    #include <arpa/inet.h>
    #include <ifaddrs.h>
    #include <netinet/in.h>
}

int main()
{
    struct ifaddrs *ifAddrStruct = NULL;
    void *tmpAddrPtr = NULL;

    getifaddrs(&ifAddrStruct);
    while (ifAddrStruct != NULL)    
    {
        if (ifAddrStruct->ifa_addr->sa_family == AF_INET)
        {
            tmpAddrPtr = &((struct sockaddr_in *)ifAddrStruct->ifa_addr)->sin_addr;
            char addressBuffer[INET_ADDRSTRLEN];
            inet_ntop(AF_INET, tmpAddrPtr, addressBuffer, INET_ADDRSTRLEN);

            if (strcmp(ifAddrStruct->ifa_name, "eth0") == 0)
            {
                std::cout << "eth0: " << addressBuffer << std::endl;
                break;
            }
            else if (strcmp(ifAddrStruct->ifa_name, "wlan0") == 0)
            {
                std::cout << "wlan0: " << addressBuffer << std::endl;
                break;
            }
        }
        ifAddrStruct = ifAddrStruct->ifa_next;
    }
}

在这里插入图片描述

2.获取磁盘信息

磁盘信息

/**
 * @file getDiskInfo.cpp
 * @author IYATT-yx
 * @brief 获取磁盘使用信息
 * @details Ubuntu 20.04 64-bit  C++20
 */
#include <iostream>

extern "C"
{
    #include <sys/vfs.h>
    #include <unistd.h>
}

struct statfs diskInfo;

int main()
{
    statfs("/", &diskInfo);
    long long unsigned totalBlocks = diskInfo.f_bsize;
    long long unsigned totalSize = (totalBlocks * diskInfo.f_blocks) >> 20;
    long long unsigned freeDisk = (diskInfo.f_bfree * totalBlocks) >> 20;

    std::cout << "磁盘总大小: " << totalSize << " MB"
                << "\n空闲大小: " << freeDisk << " MB" << std::endl;
}

在这里插入图片描述

3.CPU使用率

计算原理 (仅供参考):
将每两次读取 /proc/stat 中的数据计算差值 (源数据是从计算机启动开始计时到读取时的时间), 然后实现计算 (user + nice + system + iowait + irq + softifq) / (user + nice + system + idle + iowait + irq + softirq) 作为CPU使用率

第一行的数据解释
user从系统启动开始累计到当前时刻,处于用户态的运行时间,不包含 nice值为负进程
nice从系统启动开始累计到当前时刻,nice值为负的进程所占用的CPU时间
system从系统启动开始累计到当前时刻,处于核心态的运行时间
idle从系统启动开始累计到当前时刻,除IO等待时间以外的其它等待时间
iowait从系统启动开始累计到当前时刻,IO等待时间
irq从系统启动开始累计到当前时刻,硬中断时间
softirq从系统启动开始累计到当前时刻,软中断时间
/**
 * @file getCpuUsage.cpp
 * @author IYATT-yx
 * @brief 计算CPU使用率
 * @details Ubuntu 20.04 64-bit  C++20
 */
#include <iostream>
#include <fstream>

extern "C"
{
    #include <unistd.h>
}

int main()
{
    std::string cpu;
    std::ifstream readCPU;

    readCPU.open("/proc/stat", std::ifstream::in);
    long luser, lnice, lsys, lidle, liowait, lirq, lsoftirq, ltotal;
    readCPU >> cpu >> luser >> lnice >> lsys >> lidle >> liowait >> lirq >> lsoftirq;
    ltotal = luser + lnice + lsys + lidle + liowait + lirq + lsoftirq;
    readCPU.close();

    while (true)
    {
        sleep(2);
        
        readCPU.open("/proc/stat", std::ifstream::in);
        long  user, nice, sys, idle, iowait, irq, softirq, total;
        readCPU >> cpu >> user >> nice >> sys >> idle >> iowait >> irq >> softirq;
        readCPU.close();
        total = user + nice + sys + idle + iowait + irq + softirq;
        long usage = static_cast<long>(static_cast<double>(total - ltotal - (idle - lidle)) / static_cast<double>(total - ltotal) * 100);
        std::cout << "CPU使用率: " << usage << " %" << std::endl;

        luser = user;
        lnice = nice;
        lsys = sys;
        lidle = idle;
        liowait = iowait;
        lirq = irq;
        lsoftirq = softirq;
        ltotal = total;
    }
} 

在这里插入图片描述

4.获取CPU温度 (仅树莓派可用)

/**
 * @file getCpuTemp.cpp
 * @author IYATT-yx
 * @brief 获取CPU温度
 * @details Raspberry Pi 4B 1.1  Raspberry Pi OS 64-bit beta (2020-8-24)  C++20
 */
#include <iostream>
#include <fstream>

extern "C"
{
    #include <unistd.h>
}

int main()
{
    std::ifstream cpuTemp;
    long temp;

    while (true)
    {
        cpuTemp.open("/sys/class/thermal/thermal_zone0/temp", std::ifstream::in);
        cpuTemp >> temp;
        std::cout << "CPU温度为: " << static_cast<double>(temp) / 1000 << std::endl;
        cpuTemp.close();
        sleep(1);
    }
}

在这里插入图片描述

5.获取内存和交换分区信息

1

/**
 * @file getRamInfo.cpp
 * @author IYATT-yx
 * @brief 获取内存和交换分区信息
 * @details Ubuntu 20.04 64-bit  C++20
 */
#include <iostream>

extern "C"
{
    #include <sys/sysinfo.h>
    #include <unistd.h>
}

struct sysinfo sysInfo;

int main()
{
    system("clear");
    while (true)
    {
        if (sysinfo(&sysInfo) != 0)
        {
            std::cerr << "sysinfo Error" << std::endl;
            continue;
        }

        unsigned long totalRAM = sysInfo.totalram >> 20;
        unsigned long freeRAM = sysInfo.freeram >> 20;
        unsigned long sharedRam = sysInfo.sharedram >> 20;
        unsigned long buffersRam = sysInfo.bufferram >> 20;

        std::cout << "total: " << totalRAM << "  MB\n"
                    << "free: " << freeRAM << "  MB\n"
                    << "shared: " << sharedRam << "  MB\n"
                    << "buff/cache: " << buffersRam << "  MB\n" << std::endl;

        unsigned long totalSwap = sysInfo.totalswap >> 20;
        unsigned long freeSwap = sysInfo.freeswap >> 20;

        std::cout << "total swap: " << totalSwap << " MB\n"
                    << "free swap: " << freeSwap << "MB" << std::endl; 

        sleep(1);
        system("clear");
    }
}

在这里插入图片描述

2

/**
 * @file getRamInfo.cpp
 * @author IYATT-yx
 * @brief 获取内存和交换分区信息
 * @details Raspberry Pi 4B 1.1  Raspberry Pi OS 64-bit beta (2020-8-24)  C++20
 */
#include <iostream>
#include <fstream>
#include <string>

int main()
{
    std::ifstream ifs("/proc/meminfo", std::ifstream::in);
    // 读取值
    long value;
    // 匹配项目名字 占位
    std::string itemName, strNULL;

    while (itemName != "MemTotal:")
    {
        ifs >> itemName >> value >> strNULL;
    }
    std::cout << "总内存: " << (value >> 10) << "MB" << std::endl;

    while (itemName != "MemFree:")
    {
        ifs >> itemName >> value >> strNULL;
    }
    std::cout << "未使用内存: " << (value >> 10) << "MB" << std::endl;

    while (itemName != "MemAvailable:")
    {
        ifs >> itemName >> value >> strNULL;
    }
    std::cout << "可用内存:" <<  (value >> 10) << "MB" << std::endl;

    while (itemName != "Buffers:")
    {
        ifs >> itemName >> value >> strNULL;
    }
    std::cout << "缓冲区: " << (value >> 10) << "MB" << std::endl;

    while (itemName != "Cached:")
    {
        ifs >> itemName >> value >> strNULL;
    }
    std::cout << "页高速缓存: " << (value >> 10) << "MB" << std::endl;

    while (itemName != "SwapTotal:")
    {
        ifs >> itemName >> value >> strNULL;
    }
    std::cout << "交换分区总大小: " << (value >> 10) << "MB" << std::endl;

    while (itemName != "SwapFree:")
    {
        ifs >> itemName >> value >> strNULL;
    }
    std::cout << "交换分区未使用大小: " << (value >> 10) << "MB" << std::endl;
}

在这里插入图片描述


版权声明:本文为weixin_45579994原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。