"Fossies" - the Fresh Open Source Software Archive

Member "linux_logo-6.0/libsysinfo-0.3.0/Linux/sysinfo_linux.c" (8 May 2020, 5549 Bytes) of package /linux/misc/linux_logo-6.0.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file.

    1 #include <stdio.h>
    2 #include <stdlib.h>      /* atol, strtol   */
    3 #include <string.h>      /* strncmp, strstr,strchr */
    4 #include <ctype.h>       /* isdigit */
    5 #include <sys/stat.h>    /* stat */
    6 #include <unistd.h>      /* stat */
    7 
    8 #include <sys/sysinfo.h> /* sysinfo() */
    9 
   10 #include "../sysinfo.h"
   11 #include "../include/uname.h"
   12 
   13 
   14     /* This code originally modeled on linux sh-utils 1.16 uptime.c code */
   15     /* breaks for uptimes of over 2^31 seconds.  Is that a problem? */
   16 int get_uptime (void) {
   17 
   18     FILE *fff;
   19     float exact_uptime;
   20     int uptime_seconds=-1;
   21     int result;
   22 
   23     fff=fopen("/proc/uptime","r");
   24     if (fff!=NULL) {
   25         result=fscanf(fff,"%f",&exact_uptime);
   26         fclose (fff);
   27 
   28         if (result==1) {
   29             uptime_seconds=exact_uptime;
   30         }
   31     }
   32 
   33     return uptime_seconds;
   34 }
   35 
   36     /* Based on code contributed by */
   37     /* Anders Rundegren <anders@rundegren.com> */
   38 int get_load_average(float *load_1,float *load_5,float *load_15) {
   39 
   40     FILE *fff;
   41     int result=-1;
   42 
   43     fff=fopen("/proc/loadavg","r");
   44     if (fff!=NULL) {
   45         result=fscanf(fff,"%f" "%f" "%f", load_1, load_5, load_15);
   46         fclose (fff);
   47         if (result!=3) {
   48             result=-1;
   49         }
   50     }
   51 
   52     return result;
   53 }
   54 
   55 int get_os_info(struct os_info_type *os_info) {
   56     return uname_get_os_info(os_info);
   57 }
   58 
   59 char *get_host_name(char *hostname,char *domain) {
   60     return uname_get_host_name(hostname,domain);
   61 }
   62 
   63 
   64     /* This is a newer method to obtain memory info from /proc/iomem memory
   65      * map under 2.4.x. It should work with ACPI systems too. */
   66     /* Originally Contributed by Sitsofe Wheeler <sits@sucs.swan.ac.uk> */
   67     /* Improved a bit (in theory) to handle 64-bit machines -vmw */
   68 
   69     /* Modern systems are zeroing out the addresses in */
   70     /* /proc/iomem for security reasons, which makes this useless */
   71 
   72 long long get_mem_size_iomem(void) {
   73 
   74     unsigned long long mem_size=0,begin,end;
   75     char *pos;
   76     char temp_string[BUFSIZ];
   77     FILE *info;
   78 
   79     if ((info=fopen("/proc/iomem", "r"))) {
   80         while (fgets(temp_string, BUFSIZ, info)) {
   81             pos=strchr(temp_string, ':');
   82             /* It's safe to +1 to pos because in the worst case */
   83             /* we will be on the end of string marker. I just   */
   84             /* hope strncmp does bounds checking */
   85             if (pos && (strncmp(pos+1, " System RAM", 10)==0 ||
   86                 strncmp(pos+1, " ACPI", 5)==0)) {
   87                     /* Extract the upper memory position */
   88                     /* printf("Adding %s region ",pos); */
   89                 pos = strchr(temp_string, '-');
   90                 if (pos) {
   91                     *pos=0;
   92                     end=strtoull(pos+1, NULL, 16);
   93                     begin=strtoull(temp_string,NULL,16);
   94                     mem_size+=(end-begin);
   95                     /* printf("%lld bytes\n",(end-begin)); */
   96                 }
   97             }
   98         }
   99         fclose(info);
  100         /* printf("Final size=%lld\n",mem_size); */
  101     }
  102 
  103     if (mem_size > 0) {
  104 
  105         /* if over, round up */
  106         if (mem_size%(1024*1024)) {
  107             mem_size = (mem_size/(1024*1024))+1;
  108         }
  109         else {
  110             mem_size = (mem_size/(1024*1024));
  111         }
  112 
  113         return mem_size;
  114     }
  115     else {
  116         return 0;
  117     }
  118 }
  119 
  120 
  121     /* mem_size in megabytes by statting /proc/kcore */
  122     /* This won't work on 32bit machines with > 2Gig of RAM */
  123 long long get_mem_size_stat(void) {
  124 
  125     long long mem_size=0;
  126     struct stat buff;
  127 
  128     stat("/proc/kcore",&buff);
  129     mem_size=buff.st_size;
  130     mem_size/=(1024*1024);
  131 
  132     return mem_size;
  133 }
  134 
  135 long long get_mem_size_sysinfo(void) {
  136 
  137     long long mem_size=0;
  138     struct sysinfo system_info;
  139 
  140     sysinfo(&system_info);
  141 
  142     mem_size=(system_info.totalram*system_info.mem_unit)/(1024*1024);
  143 
  144     return mem_size;
  145 
  146 }
  147 
  148     /* get mem size from /proc/meminfo */
  149 long long get_mem_size_meminfo(void) {
  150 
  151     long long mem_size=0;
  152     char temp_string[BUFSIZ];
  153     FILE *info;
  154     int position=0;
  155 
  156     info=fopen("/proc/meminfo", "r");
  157 
  158     if (info==NULL) {
  159         printf("Error opening /proc/meminfo!\n");
  160         return 0;
  161     }
  162 
  163     while (fgets(temp_string, BUFSIZ, info)) {
  164         position=0;
  165         /* Skip label */
  166         while (temp_string[position]) {
  167             if (isdigit(temp_string[position])) break;
  168             position++;
  169         }
  170 
  171         /* Grab values (in kb) */
  172         if (strstr(temp_string, "MemTotal")) {
  173             mem_size = atoll(temp_string+position);
  174         }
  175     }
  176     fclose(info);
  177 
  178     return mem_size/1024ULL;
  179 }
  180 
  181 
  182     /* Try to intelligently figure out which memory method is best */
  183     /* /proc/iomem used to give the closest to the "expected" */
  184     /* value but is mostly useless now due to security reasons */
  185 
  186 long long get_mem_size(void) {
  187 
  188     long long mem_size=0;
  189 
  190     /* First try any arch-specific memsize functions */
  191     mem_size=get_arch_specific_mem_size();
  192 
  193     if (mem_size == MEM_USE_MEMINFO) {
  194         mem_size = 0;
  195         goto use_meminfo;
  196     }
  197 
  198     if (mem_size == MEM_USE_SYSINFO) {
  199         mem_size = 0;
  200         goto use_sysinfo;
  201     }
  202 
  203     /* Next try the 2.4.x+ method of iomem */
  204     /* This breaks on moden (5.x?) systems */
  205     if (mem_size == 0) {
  206         mem_size = get_mem_size_iomem();
  207     }
  208 
  209 #if 0
  210     /* Try stat-ing /proc/kcore */
  211     /* On modern 64-bit kernels this is 128TB in size? */
  212     if (mem_size == 0) {
  213         mem_size = get_mem_size_stat();
  214     }
  215 #endif
  216 
  217 use_sysinfo:
  218 
  219     /* sysinfo should return same as /proc/meminfo */
  220     /* which, sadly, is often from 1MB-20MB off    */
  221     if (mem_size == 0) {
  222         mem_size = get_mem_size_sysinfo();
  223     }
  224 
  225 use_meminfo:
  226     /* If all else fails, try using /proc/meminfo */
  227     if (mem_size == 0) {
  228         mem_size = get_mem_size_meminfo();
  229     }
  230 
  231     return mem_size;
  232 }
  233 
  234 double get_cpu_mhz(void) {
  235 
  236     struct cpu_info_type cpu_info;
  237     double megahertz=0.0;
  238     long long temp;
  239     FILE *fff;
  240 
  241     fff=fopen("/sys/devices/system/cpu/cpu0/cpufreq/cpuinfo_max_freq","r");
  242     if (fff!=NULL) {
  243         fscanf(fff,"%lld",&temp);
  244         megahertz=(double)temp;
  245         megahertz/=1000.0;
  246         fclose(fff);
  247     }
  248 
  249     if (megahertz==0.0) {
  250         /* Couldn't read from cpufreq, instead use /proc/cpuinfo */
  251 
  252         get_cpu_info(&cpu_info);
  253 
  254         megahertz=(double)cpu_info.megahertz;
  255     }
  256 
  257     return megahertz;
  258 }
  259 
  260