Question

Je voudrais savoir si quelqu'un ici a quelques bons exemples d'implémentation C ++ CPUID qui peut être référencé à partir de l'une des langues .net gérés.

En outre, si cela ne pas être le cas, dois-je être au courant de certaines différences de mise en œuvre entre X86 et X64?

Je voudrais utiliser CPUID pour obtenir des informations sur la machine mon logiciel fonctionne sur (crashreporting etc ...) et je veux garder tout aussi largement compatible que possible.

Raison principale Je demande parce que je suis un noob totale en ce qui concerne l'écriture ce qui sera probablement toutes les instructions de la machine que j'ai des connaissances de base sur les registres CPU et ainsi de suite ...

Avant que les gens commencent à me dire à Google: J'ai trouvé quelques exemples en ligne, mais le plus souvent ils ne sont pas destinés à permettre une interaction du code managé et aucun des exemples ont été visant à la fois et X64 X86. La plupart des exemples semblaient X86 spécifiques.

Était-ce utile?

La solution

Accès aux informations CPUID premières est en fait très simple, voici une classe C ++ ce qui fonctionne sous Windows, Linux et Mac OS X:

#ifndef CPUID_H
#define CPUID_H

#ifdef _WIN32
#include <limits.h>
#include <intrin.h>
typedef unsigned __int32  uint32_t;

#else
#include <stdint.h>
#endif

class CPUID {
  uint32_t regs[4];

public:
  explicit CPUID(unsigned i) {
#ifdef _WIN32
    __cpuid((int *)regs, (int)i);

#else
    asm volatile
      ("cpuid" : "=a" (regs[0]), "=b" (regs[1]), "=c" (regs[2]), "=d" (regs[3])
       : "a" (i), "c" (0));
    // ECX is set to zero for CPUID function 4
#endif
  }

  const uint32_t &EAX() const {return regs[0];}
  const uint32_t &EBX() const {return regs[1];}
  const uint32_t &ECX() const {return regs[2];}
  const uint32_t &EDX() const {return regs[3];}
};

#endif // CPUID_H

Pour utiliser juste instancier une instance de la classe, charger l'instruction CPUID vous intéresse et examiner les registres. Par exemple:

#include "CPUID.h"

#include <iostream>
#include <string>

using namespace std;

int main(int argc, char *argv[]) {
  CPUID cpuID(0); // Get CPU vendor

  string vendor;
  vendor += string((const char *)&cpuID.EBX(), 4);
  vendor += string((const char *)&cpuID.EDX(), 4);
  vendor += string((const char *)&cpuID.ECX(), 4);

  cout << "CPU vendor = " << vendor << endl;

  return 0;
}

Cette page Wikipédia indique comment utiliser CPUID: http://en.wikipedia.org/wiki/CPUID

EDIT: Ajout #include <intrin.h> pour Windows, par commentaires

.

Autres conseils

Voir cet article MSDN sur les __cpuid.

Il y a un échantillon complet qui compile avec Visual Studio 2005 ou mieux. Pour Visual Studio 6, vous pouvez utiliser cette place du compilateur instrinsic __cpuid:

void __cpuid(int CPUInfo[4], int InfoType)
{
 __asm 
  {
     mov    esi, CPUInfo
     mov    eax, InfoType
     xor    ecx, ecx  
     cpuid  
     mov    dword ptr [esi +  0], eax
     mov    dword ptr [esi +  4], ebx  
     mov    dword ptr [esi +  8], ecx  
     mov    dword ptr [esi + 12], edx  
  }
}

Pour Visual Studio 2005, vous pouvez l'utiliser au lieu du compilateur instrinsic __cpuidex:

void __cpuidex(int CPUInfo[4], int InfoType, int ECXValue)
{
 __asm 
  {
     mov    esi, CPUInfo
     mov    eax, InfoType
     mov    ecx, ECXValue
     cpuid  
     mov    dword ptr [esi +  0], eax
     mov    dword ptr [esi +  4], ebx  
     mov    dword ptr [esi +  8], ecx  
     mov    dword ptr [esi + 12], edx  
  }
}

Peut-être pas exactement ce que vous cherchez, mais Intel avez bon article et exemple de code pour les architectures de plate-forme énumération de bits Intel 64 (processeur, mémoire cache, etc.) qui semble aussi couvrir 32 bits des processeurs x86.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top