Differenze tra le versioni di "Controllare la temperatura dell'hardware mediante le funzioni del API di libsensors"

Da Gambas-it.org - Wikipedia.
Riga 1: Riga 1:
La libreria '''''Libsensors''''' mette a disposizioni risorse per poter effettuare controlli su alcune parti ed aspetti dell'hardware per Linux. In particolare, ad esempio, questa libreria consente di gestire e visualizzare i dati del sensore della temperatura dell'hardware principale.
+
La libreria '''''Libsensors''''' mette a disposizione risorse per poter effettuare controlli su alcune parti ed aspetti dell'hardware per Linux. In particolare, ad esempio, questa libreria consente di gestire e visualizzare i dati del sensore della temperatura dell'hardware principale.
  
 
In un dato sistema, ci possono essere uno o più chip di controllo hardware. I nomi delle funzioni sono standardizzati. Ogni funzione può a sua volta avere uno o più sub-caratteristiche , ognuna di esse rappresenta un attributo della funzione: valore di ingresso , limite inferiore , limite superiore, limite di allarme, ecc. I nomi delle sub-funzionalità sono anch'essi predefiniti. Le sub-caratteristiche effettivamente esistenti dipendono dal tipo di chip presente nel sistema hardware.
 
In un dato sistema, ci possono essere uno o più chip di controllo hardware. I nomi delle funzioni sono standardizzati. Ogni funzione può a sua volta avere uno o più sub-caratteristiche , ognuna di esse rappresenta un attributo della funzione: valore di ingresso , limite inferiore , limite superiore, limite di allarme, ecc. I nomi delle sub-funzionalità sono anch'essi predefiniti. Le sub-caratteristiche effettivamente esistenti dipendono dal tipo di chip presente nel sistema hardware.
Riga 25: Riga 25:
 
===Esempio pratico===
 
===Esempio pratico===
 
Di seguito mostriamo un semplice, breve ed essenziale esempio di codice per monitorare la temperatura dell'hardware:
 
Di seguito mostriamo un semplice, breve ed essenziale esempio di codice per monitorare la temperatura dell'hardware:
  Library "libsensors:4.3.2"
+
Library "libsensors:4.3.2"
 
    
 
    
 
  Public Struct sensors_bus_id
 
  Public Struct sensors_bus_id
Riga 38: Riga 38:
 
   path As Pointer
 
   path As Pointer
 
  End Struct
 
  End Struct
 
Private scnm As New Sensors_chip_name
 
 
   
 
   
 
  Public Struct sensors_feature
 
  Public Struct sensors_feature
Riga 48: Riga 46:
 
   padding1 As Integer
 
   padding1 As Integer
 
  End Struct
 
  End Struct
 
Private sf As New Sensors_feature
 
 
   
 
   
 
  Public Struct sensors_subfeature
 
  Public Struct sensors_subfeature
Riga 58: Riga 54:
 
   flags As Integer
 
   flags As Integer
 
  End Struct
 
  End Struct
 
Private subf As New Sensors_subfeature
 
 
   
 
   
 
  Private Const SENSORS_MODE_R As Byte = 1
 
  Private Const SENSORS_MODE_R As Byte = 1
Riga 85: Riga 79:
 
  <FONT color=gray>' ''int sensors_snprintf_chip_name(char *str, size_t size, const sensors_chip_name *chip)''
 
  <FONT color=gray>' ''int sensors_snprintf_chip_name(char *str, size_t size, const sensors_chip_name *chip)''
 
  ' ''Prints a chip name from its internal representation. Return the number of characters printed on success (same as snprintf), <0 on error.''</font>
 
  ' ''Prints a chip name from its internal representation. Return the number of characters printed on success (same as snprintf), <0 on error.''</font>
  Private Extern sensors_snprintf_chip_name(strB As Byte[], size As Integer, chip As Sensors_chip_name) As Integer
+
  Private Extern sensors_snprintf_chip_name(strp As Pointer, size As Integer, chip As Sensors_chip_name) As Integer
 
   
 
   
 
  <FONT color=gray>' ''const char* sensors_get_adapter_name (const sensors_bus_id * bus)''
 
  <FONT color=gray>' ''const char* sensors_get_adapter_name (const sensors_bus_id * bus)''
Riga 98: Riga 92:
 
  '''Public''' Sub Main()
 
  '''Public''' Sub Main()
 
   
 
   
 +
  Dim scnm As Sensors_chip_name
 +
  Dim sf As Sensors_feature
 +
  Dim subf As Sensors_subfeature
 
   Dim nomeB As New Byte[128]
 
   Dim nomeB As New Byte[128]
 
   Dim c, lung, f, s, rc As Integer
 
   Dim c, lung, f, s, rc As Integer
 
   Dim valTemp As Float
 
   Dim valTemp As Float
 
    
 
    
 +
  If sensors_init(Null) <> 0 Then Error.Raise("Impossibile inizializzare la libreria 'libsensors' !")
 +
 
 +
  scnm = sensors_get_detected_chips(0, VarPtr(c))
 
   
 
   
    If sensors_init(Null) <> 0 Then Print Error.Raise("Impossibile inizializzare la libreria 'libsensors' !")
+
  lung = sensors_snprintf_chip_name(nomeB.Data, 128, scnm)
+
  Print nomeB.ToString(0, lung)
    scnm = sensors_get_detected_chips(0, VarPtr(c))
 
 
    lung = sensors_snprintf_chip_name(nomeB, 128, scnm)
 
    Print nomeB.ToString(0, lung)
 
 
    
 
    
    Print "Adapter: "; sensors_get_adapter_name(scnm.bus)
+
  Print "Adapter: "; sensors_get_adapter_name(scnm.bus)
   
 
 
    sf = sensors_get_features(scnm, VarPtr(f))
 
 
      
 
      
    Print "Tipo di sensore termico: "; sf_type(sf.type)
+
  sf = sensors_get_features(scnm, VarPtr(f))
 
      
 
      
    Print
+
  Print "Tipo di sensore termico: "; sf_type(sf.type)
 +
  Print
 
   
 
   
 +
  subf = sensors_get_all_subfeatures(scnm, sf, VarPtr(s))
 +
  If subf.flags And SENSORS_MODE_R Then
 +
    rc = sensors_get_value(scnm, subf.number, VarPtr(valTemp))
 +
    If rc < 0 Then
 +
      Error.Raise("Errore nella lettura del valore !")
 +
    Else
 +
      Print String@(sf.name); " = "; valTemp; "°"
 +
    Endif
 +
  Endif
 +
 
 +
  Print ".........................................\n"
 
      
 
      
    subf = sensors_get_all_subfeatures(scnm, sf, VarPtr(s))
+
  scnm = sensors_get_detected_chips(0, VarPtr(c))
    If subf.flags And SENSORS_MODE_R Then
+
 
      rc = sensors_get_value(scnm, subf.number, VarPtr(valTemp))
+
  lung = sensors_snprintf_chip_name(nomeB.Data, 128, scnm)
      If rc < 0 Then
+
  Print nomeB.ToString(0, lung)
        Error.Raise("Errore nella lettura del valore !")
+
  Print "Adapter: "; sensors_get_adapter_name(scnm.bus)
      Else
+
  Print "Tipo di sensore termico: "; sf_type(sf.type)
        Print String@(sf.name); " = "; valTemp; "°"
+
  Print
      Endif
+
 
    Endif
+
  If subf.flags And SENSORS_MODE_R Then  
+
    rc = sensors_get_value(scnm, subf.number, VarPtr(valTemp))
+
    If rc < 0 Then
    Print ".........................................\n"
+
      Error.Raise("Errore nella lettura del valore !")
+
    Else
+
      Print "Temperatura CPU = "; valTemp; "°"
    scnm = sensors_get_detected_chips(0, VarPtr(c))
+
    Endif
+
  Endif
    lung = sensors_snprintf_chip_name(nomeB, 128, scnm)
+
 
    Print nomeB.ToString(0, lung)
+
  Print "'''''''''''''''''''''''''''''''''''''''''"
+
 
    Print "Adapter: "; sensors_get_adapter_name(scnm.bus)
+
  <FONT color=gray>' ''Va in chiusura:''</font>
+
  sensors_cleanup()
    Print "Tipo di sensore termico: "; sf_type(sf.type)
+
 
    Print
 
 
    If subf.flags And SENSORS_MODE_R Then  
 
      rc = sensors_get_value(scnm, subf.number, VarPtr(valTemp))
 
      If rc < 0 Then
 
        Error.Raise("Errore nella lettura del valore !")
 
      Else
 
        Print "Temperatura CPU = "; valTemp; "°"
 
      Endif
 
    Endif
 
 
 
    Print "'''''''''''''''''''''''''''''''''''''''''"
 
 
<FONT color=gray>' ''Va in chiusura:''</font>
 
    sensors_cleanup()
 
 
 
  '''End'''
 
  '''End'''
+
 
 
 
   
 
   
 
  '''Private''' Function sf_type(numero As Byte) As String
 
  '''Private''' Function sf_type(numero As Byte) As String
Riga 167: Riga 154:
 
   Dim tipo As String
 
   Dim tipo As String
 
    
 
    
    Select Case numero
+
  Select Case numero
      Case 1
+
    Case 1
        tipo = "PII/Celeron Diode"
+
      tipo = "PII/Celeron Diode"
      Case 2
+
    Case 2
        tipo = "3904 transistor"
+
      tipo = "3904 transistor"
      Case 3
+
    Case 3
        tipo = "thermal diode"
+
      tipo = "thermal diode"
      Case 4
+
    Case 4
        tipo = "thermistor"
+
      tipo = "thermistor"
      Case 5
+
    Case 5
        tipo = "AMD AMDSI"
+
      tipo = "AMD AMDSI"
      Case 6
+
    Case 6
        tipo = "Intel PECI"
+
      tipo = "Intel PECI"
    End Select
+
  End Select
 
      
 
      
    Return tipo
+
  Return tipo
 
+
 
 
  '''End'''
 
  '''End'''
  

Versione delle 02:45, 24 gen 2017

La libreria Libsensors mette a disposizione risorse per poter effettuare controlli su alcune parti ed aspetti dell'hardware per Linux. In particolare, ad esempio, questa libreria consente di gestire e visualizzare i dati del sensore della temperatura dell'hardware principale.

In un dato sistema, ci possono essere uno o più chip di controllo hardware. I nomi delle funzioni sono standardizzati. Ogni funzione può a sua volta avere uno o più sub-caratteristiche , ognuna di esse rappresenta un attributo della funzione: valore di ingresso , limite inferiore , limite superiore, limite di allarme, ecc. I nomi delle sub-funzionalità sono anch'essi predefiniti. Le sub-caratteristiche effettivamente esistenti dipendono dal tipo di chip presente nel sistema hardware.

La descrizione chip, restituita dall'apposita funzione esterna sensors_snprintf_chip_name(), è formata da più elementi, separati da trattini. Il primo elemento è il tipo di chip, il secondo elemento è il nome del bus, e il terzo elemento è l'indirizzo esadecimale del chip.

Riguardo alla configurazione della temperatura dei chip essa può avere due specifici sub-caratteristiche:

  • tipo di sensore di temperatura (tempX_type);
  • valori di isteresi (tempX_max_hyst e tempX_crit_hyst).

I tipi di sensori termici disponibili sono:
1 PII/Celeron Diode
2 3904 transistor
3 thermal diode
4 thermistor
5 AMD AMDSI
6 Intel PECI

L'Isteresi è la capacità di molti chip di far scattare un allarme quando la temperatura supera il suo limite massimo e critico previsto per quel chip, e di far cessare l'allarme quando la temperatura scende al di sotto di quel limite critico. Quindi , oltre a tempX_max, molti chip hanno una caratteristica secondaria: tempX_max_hyst e tempX_crit_hyst.


Per poter fruire delle risorse esterne della libreria libsensors, si dovrà richiamare l'attuale libreria: libsensors.so.4.3.2 .


Esempio pratico

Di seguito mostriamo un semplice, breve ed essenziale esempio di codice per monitorare la temperatura dell'hardware:

Library "libsensors:4.3.2"
 
Public Struct sensors_bus_id
  type As Short
  nr As Short
End Struct

Public Struct sensors_chip_name
  prefix As Pointer
  bus As Struct Sensors_bus_id
  addr As Integer
  path As Pointer
End Struct

Public Struct sensors_feature
  name As Pointer
  number As Integer
  type As Integer
  first_subfeature As Integer   ' Questi ultimi due campi servono soltanto per un uso interno alla libreria "libsensors"
  padding1 As Integer
End Struct

Public Struct sensors_subfeature
  name As Pointer
  number As Integer
  type As Integer
  mapping As Integer
  flags As Integer
End Struct

Private Const SENSORS_MODE_R As Byte = 1

' int sensors_init(FILE *input)
' Load the configuration file and the detected chips list. If this returns a value unequal to zero, you are in trouble
Private Extern sensors_init(filename As File) As Integer

' const sensors_chip_name *sensors_get_detected_chips(const sensors_chip_name *match, int *nr)
' This function returns all detected chips that match a given chip name, one by one. If no chip name is provided, all detected chips are returned.
Private Extern sensors_get_detected_chips(scnMatch As Pointer, nrP As Pointer) As Sensors_chip_name

' const sensors_feature * sensors_get_features(const sensors_chip_name *name, int *nr)
' This returns all main features of a specific chip. nr is an internally used variable. Set it to zero to start at the begin of the list. If no more features are found NULL is returned.
Private Extern sensors_get_features(chip_name As Sensors_chip_name, nrP As Pointer) As Sensors_feature

' const sensors_subfeature * sensors_get_all_subfeatures(const sensors_chip_name *name, const sensors_feature *feature, int *nr)
' This returns all subfeatures of a given main feature. nr is an internally used variable. Set it to zero to start at the begin of the list. If no more features are found NULL is returned.
Private Extern sensors_get_all_subfeatures(chip_name As Sensors_chip_name, feature As Sensors_feature, nrP As Pointer) As Sensors_subfeature

' int sensors_get_value(const sensors_chip_name *name, int subfeat_nr, double *value)
' Read the value of a subfeature of a certain chip. his function will return 0 on success, and <0 on failure.
Private Extern sensors_get_value(chip_name As Sensors_chip_name, subfeat_nr As Integer, value As Pointer) As Integer

' int sensors_snprintf_chip_name(char *str, size_t size, const sensors_chip_name *chip)
' Prints a chip name from its internal representation. Return the number of characters printed on success (same as snprintf), <0 on error.
Private Extern sensors_snprintf_chip_name(strp As Pointer, size As Integer, chip As Sensors_chip_name) As Integer

' const char* sensors_get_adapter_name (const sensors_bus_id * bus)
' Returns the adapter name of a bus number, as used within the sensors_chip_name structure. If it could not be found, it returns NULL.
Private Extern sensors_get_adapter_name(bus_id As Sensors_bus_id) As String

' void sensors_cleanup(void)
' Cleans everything up: you can't access anything after this, until the next sensors_init() call!
Private Extern sensors_cleanup()


Public Sub Main()

 Dim scnm As Sensors_chip_name
 Dim sf As Sensors_feature
 Dim subf As Sensors_subfeature
 Dim nomeB As New Byte[128]
 Dim c, lung, f, s, rc As Integer
 Dim valTemp As Float
  
  If sensors_init(Null) <> 0 Then Error.Raise("Impossibile inizializzare la libreria 'libsensors' !")
  
  scnm = sensors_get_detected_chips(0, VarPtr(c))

  lung = sensors_snprintf_chip_name(nomeB.Data, 128, scnm)
  Print nomeB.ToString(0, lung)
 
  Print "Adapter: "; sensors_get_adapter_name(scnm.bus)
   
  sf = sensors_get_features(scnm, VarPtr(f))
   
  Print "Tipo di sensore termico: "; sf_type(sf.type)
  Print

  subf = sensors_get_all_subfeatures(scnm, sf, VarPtr(s))
  If subf.flags And SENSORS_MODE_R Then 
    rc = sensors_get_value(scnm, subf.number, VarPtr(valTemp))
    If rc < 0 Then
      Error.Raise("Errore nella lettura del valore !")
    Else
      Print String@(sf.name); " = "; valTemp; "°"
    Endif
  Endif
  
  Print ".........................................\n"
   
  scnm = sensors_get_detected_chips(0, VarPtr(c))
  
  lung = sensors_snprintf_chip_name(nomeB.Data, 128, scnm)
  Print nomeB.ToString(0, lung)
  Print "Adapter: "; sensors_get_adapter_name(scnm.bus)
  Print "Tipo di sensore termico: "; sf_type(sf.type)
  Print
  
  If subf.flags And SENSORS_MODE_R Then 
    rc = sensors_get_value(scnm, subf.number, VarPtr(valTemp))
    If rc < 0 Then
      Error.Raise("Errore nella lettura del valore !")
    Else
      Print "Temperatura CPU = "; valTemp; "°"
    Endif
  Endif
  
  Print "''''''''''''''''''''''''''''''''''''"
  
  ' Va in chiusura:
  sensors_cleanup()
  
End
 

Private Function sf_type(numero As Byte) As String

 Dim tipo As String
 
  Select Case numero
    Case 1
      tipo = "PII/Celeron Diode"
    Case 2
      tipo = "3904 transistor"
    Case 3
      tipo = "thermal diode"
    Case 4
      tipo = "thermistor"
    Case 5
      tipo = "AMD AMDSI"
    Case 6
      tipo = "Intel PECI"
  End Select
   
  Return tipo
  
End



Riferimenti

[1] La pagina del API di lm_sensors .

[2] La pagina relativa al file sensors.conf.