web-dev-qa-db-fra.com

Générer un identifiant unique de machine

J'ai besoin d'écrire une fonction qui génère un identifiant unique pour une machine exécutant un système d'exploitation Windows.

Actuellement, j'utilise WMI pour interroger divers paramètres matériels, les concaténer et les hacher pour en déduire l'identifiant unique. Ma question est la suivante: quels sont les paramètres suggérés que je devrais utiliser? Actuellement, j'utilise une combinaison de données bios\cpu\disk pour générer l'identifiant unique. Et j'utilise le premier résultat s'il y a plusieurs résultats pour chaque métrique.

Cependant, je me suis heurté à un problème dans lequel une machine qui effectue un double amorçage sous 2 systèmes d’exploitation Windows différents génère des codes de site différents sur chaque système d’exploitation, ce qui ne devrait idéalement pas se produire.

Pour référence, voici les mesures que j'utilise actuellement:

Win32_Processor:UniqueID,ProcessorID,Name,Manufacturer,MaxClockSpeed
Win32_BIOS:Manufacturer
Win32_BIOS:SMBIOSBIOSVersion,IdentificationCode,SerialNumber,ReleaseDate,Version
Win32_DiskDrive:Model, Manufacturer, Signature, TotalHeads
Win32_BaseBoard:Model, Manufacturer, Name, SerialNumber
Win32_VideoController:DriverVersion, Name
97
HS.

Analyser le SMBIOS vous-même et le hacher à une longueur arbitraire. Voir la spécification PDF pour toutes les structures SMBIOS disponibles.

Pour interroger les informations SMBIOS de Windows, vous pouvez utiliser EnumSystemFirmwareEntries , EnumSystemFirmwareTables et GetSystemFirmwareTable .

IIRC, "l'identifiant unique" de l'instruction CPUID est obsolète à partir de P3 et plus récent.

22
Jonas Gulle

J'ai eu le même problème et après une petite recherche, j'ai décidé que le mieux serait de lire MachineGuid dans la clé de registre HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Cryptography, comme l'a suggéré @Agnus. Il est généré lors de l'installation du système d'exploitation et ne changera que si vous effectuez une nouvelle installation du système d'exploitation. Selon la version du système d'exploitation, il peut contenir l'adresse MAC de la carte réseau intégrée (ainsi que d'autres numéros, notamment aléatoires), ou un nombre pseudo-aléatoire, la dernière pour les versions de système d'exploitation plus récentes (après XP SP2, je crois, mais je ne suis pas sûr ). Si c'est théoriquement pseudo-aléatoire, il peut être falsifié - si deux machines ont le même état initial, y compris l'horloge temps réel. En pratique, cela sera rare, mais sachez si vous vous attendez à ce que ce soit une base de sécurité qui puisse être attaquée par des pirates assidus.

Bien sûr, une entrée de registre peut également être facilement modifiée par n'importe qui pour créer un GUID d'ordinateur, mais ce que j'ai trouvé c'est que cela perturberait le fonctionnement normal de nombreux composants de Windows qu'aucun utilisateur habituel ne le ferait (encore une fois, faites attention à pour les pirates hardcore).

71
Fabio Ceconello

Avec notre outil de licence nous considérons les composants suivants

  • Adresse Mac
  • CPU (Pas le numéro de série, mais le profil actuel de la CPU, comme pas à pas et modèle)
  • Numéro de série du lecteur système (pas le numéro de volume)
  • Mémoire
  • Modèle de CD-ROM et fournisseur
  • Modèle de carte vidéo et fournisseur
  • Contrôleur IDE
  • Contrôleur SCSI

Cependant, plutôt que de simplement hacher les composants et créer un système réussite/échec, nous créons une empreinte comparable qui peut être utilisée pour déterminer en quoi deux profils de machine sont différents. Si l'indice de différence est supérieur à une tolérance spécifiée, demandez à l'utilisateur de l'activer à nouveau. 

Au cours des 8 dernières années, nous avons constaté, avec des centaines de milliers d'installations installées par des utilisateurs finaux, que cette combinaison permet de fournir un identifiant d'ordinateur unique et fiable, même pour les installations de machines virtuelles et d'OS clonés.

30
Paul Alexander

Qu'en est-il simplement d'utiliser l'identifiant unique du processeur?

2
gizmo

Je déteste être le gars qui dit: "Vous faites juste la mauvaise chose" (je déteste toujours ce gars;) mais ...

Doit-il être généré de manière répétée pour la machine unique? Pourriez-vous simplement attribuer l'identifiant ou créer une clé publique/privée? Peut-être que si vous pouviez générer et stocker la valeur, vous pourriez y accéder à partir des deux installations du système d'exploitation sur le même disque?

Vous avez probablement déjà exploré ces options et elles ne fonctionnent pas pour vous, mais si ce n’est pas le cas, vous devez en tenir compte.

Si ce n'est pas une question de confiance de l'utilisateur, vous pouvez simplement utiliser des adresses MAC.

2
Sam Hoice

Dans mon programme, je vérifie d'abord Terminal Server et utilise le WTSClientHardwareId. Sinon, l'adresse MAC du PC local devrait être adéquate.

Si vous voulez vraiment utiliser la liste des propriétés que vous avez fournies, omettez des éléments tels que Name et DriverVersion, Clockspeed, etc., étant donné que cela dépend probablement du système d'exploitation. Essayez de fournir les mêmes informations sur les deux systèmes d’exploitation et laissez de côté les différences.

1
AngelBlaZe

Vous devriez envisager d’utiliser l’adresse MAC de la carte réseau (si elle existe). Celles-ci sont généralement uniques mais peuvent être fabriquées. J'ai utilisé un logiciel qui génère son fichier de licence en fonction de l'adresse MAC de votre adaptateur réseau. C'est donc un moyen relativement fiable de distinguer les ordinateurs.

1
Kyle Cronin

Une bibliothèque est disponible pour obtenir des informations spécifiques au matériel: Extracteur de numéro de série du matériel (CPU, RAM, disque dur, BIOS)

1
ariwez

Pour l’une de mes applications, j’utilise le nom de l’ordinateur s’il s’agit d’un ordinateur n’appartenant pas au domaine ou le SID du compte d’ordinateur du domaine pour les ordinateurs du domaine. Mark Russinovich en parle dans cet article, Machine SID :

Le dernier cas où la duplication de SID poserait un problème est si une application distribuée utilisait des SID de machine pour identifier de manière unique les ordinateurs. Aucun logiciel Microsoft ne le fait et utiliser le SID de la machine de cette manière ne fonctionne pas uniquement parce que tous les contrôleurs de domaine ont le même SID de la machine. Les logiciels qui reposent sur des identités d'ordinateur uniques utilisent des noms d'ordinateur ou des SID de domaine d'ordinateur (le SID des comptes d'ordinateur du domaine). 

Vous pouvez accéder au SID du compte de la machine du domaine via LDAP ou System.DirectoryServices.

1
cmcginty

Pourquoi ne pas utiliser l'adresse MAC de votre carte réseau?

0
Brian Matthews

Peut-être triche-t-il un peu, mais l'adresse MAC d'un adaptateur Ethernet de machine change rarement sans la carte mère.

0
bfabry

Pouvez-vous extraire un numéro de série ou une étiquette de service du fabricant?

Notre boutique étant une boutique Dell, nous utilisons l’étiquette de service unique à chaque machine pour les identifier. Je sais que cela peut être demandé par le BIOS, du moins sous Linux, mais je ne sais pas comment le faire sous Windows.

0
Christopher Cashell

J'avais une contrainte supplémentaire, j'utilisais .net express, je ne pouvais donc pas utiliser le mécanisme de requête matérielle standard. J'ai donc décidé d'utiliser Power Shell pour effectuer la requête. Le code complet ressemble à ceci:

Private Function GetUUID() As String
    Dim GetDiskUUID As String = "get-wmiobject Win32_ComputerSystemProduct  | Select-Object -ExpandProperty UUID"
    Dim X As String = ""
    Dim oProcess As New Process()
    Dim oStartInfo As New ProcessStartInfo("powershell.exe", GetDiskUUID)
    oStartInfo.UseShellExecute = False
    oStartInfo.RedirectStandardInput = True
    oStartInfo.RedirectStandardOutput = True
    oStartInfo.CreateNoWindow = True
    oProcess.StartInfo = oStartInfo
    oProcess.Start()
    oProcess.WaitForExit()
    X = oProcess.StandardOutput.ReadToEnd
    Return X.Trim()
End Function
0
user2515235