2014-12-04 3 views
5

Ho un problema dispari. Sto tentando di restituire il numero di serie del disco rigido da WMIC a una variabile in un file batch; la linea che mi dà la variabile è:WMIC Returning Odd Serial Number

for /f "skip=2 tokens=2 delims=," %%a in ('wmic diskdrive get serialnumber /FORMAT:CSV') do (set harddisk=%%a) 

Questo assegna quello wmic vede come il numero di serie per il disco rigido a una variabile, il problema è che il numero di serie che ritorna è un po 'fuori. In un esempio restituisce:

3ZVT01H4

Ma il numero di serie sull'etichetta è:

Z3TV104H

Sembra che sta prendendo il numero di serie attuale e invertire ogni due caratteri; sto scrivendo qualcosa di sbagliato o si tratta di un problema noto (ma non documentato da nessuna parte)?

C'è un modo per prendere la variabile, dividerla in due blocchi di caratteri, invertire l'ordine di tutti quei caratteri e inserirla in una variabile?

risposta

4

- Sembra che sta prendendo il numero di serie attuale e invertire ogni due caratteri; sto scrivendo qualcosa di sbagliato o si tratta di un problema noto (ma non documentato da nessuna parte)?

Il meglio che posso immaginare, è apparently a bug. Anche i miei personaggi sono invertiti dalla coppia, e non è limitato a wmic. Stesso risultato se I SELECT SerialNumber FROM Win32_DiskDrive da winmgmts:\\localhost\root\cimv2 in WSH.

- C'è un modo per prendere la variabile, dividerla in due blocchi di caratteri, invertire l'ordine di tutti quei caratteri e inserirla in una variabile?

Se si dispone di PowerShell, è possibile farlo con uno regexp replace. Ecco uno script batch che richiama un comando PowerShell per dimostrare:

@echo off 
setlocal 

for /f "tokens=*" %%I in ('wmic diskdrive get serialnumber ^| findstr "[0-9]"') do (

    echo reversed: %%I 

    for /f "tokens=*" %%x in ('powershell -command "'%%I' -replace '(.)(.)','$2$1'"') do (
     set "serial=%%x" 
    ) 
) 

echo corrected: %serial% 

goto :EOF 

Credo che questo si qualifica come duck punch. :)

In realtà, se si desidera solo per vedere la serie senza impostare una variabile, è possibile farlo con un PowerShell one-liner:

powershell "gwmi win32_diskdrive | %{ $_.serialnumber -replace '(.)(.)','$2$1' }" 
4

Tutto ciò che serve sono alcuni cicli e operazioni di sottostringa di base.

Suppongo arbitrariamente che il numero non superi i 100 caratteri.

@echo off 
set "disk=3ZVT01H4" 
echo Before: %disk% 
call :swapChars disk 
echo After: %disk% 
exit /b 

:swapChars var 
setlocal enableDelayedExpansion 
set "rtn=" 
for /l %%A in (0 2 100) do (
    set /a "B=%%A+1" 
    for %%B in (!B!) do (
    if "!%~1:~%%B,1!" equ "" goto :break 
    set "rtn=!rtn!!%~1:~%%B,1!!%~1:~%%A,1!" 
) 
) 
:break 
endlocal & set "%~1=%rtn%" 
exit /b 
+0

Interessante. Stavo per suggerire che l'ordine dei personaggi potrebbe non essere prevedibile, ma sembra che i risultati di 'wmic diskdrive get serialnumber' nella stessa inversione di coppie di caratteri sulla mia macchina. Adesivo: 'WMAV2FA79348' ;;; WMI: 'W -DMWVAF27A3984' – rojo

0

Dopo l'aggiornamento di installare un sistema operativo Windows 7 a Windows 10, non ho avuto alcun problema a vedere il numero di serie HDD di un'unità WD visualizzato correttamente quando si utilizza: wmic diskdrive get model,name,SerialNumber,size Quindi sembra che Microsoft abbia deciso di cambiare la modalità di visualizzazione dei numeri di serie dell'unità disco fisica.

Alcune utili informazioni di fondo: Se qualcuno esegue il comando ATA a basso livello per ottenere informazioni da un disco, ogni due caratteri del nome del modello e il numero di serie sono in realtà memorizzati in ordine inverso!Questo potrebbe essere collegato a ciò che viene chiamato "little endian" o semplicemente come l'ATA ha deciso che dovrebbero essere archiviati.