<commit_before>#![cfg_attr(feature = "unstable", feature(asm))]
#![cfg_attr(not(any(target_arch = "x86_64", target_arch = "x86")), allow(dead_code))]

//! ```
//! extern crate cupid;
//!
//! fn main() {
//!     let information = cupid::master();
//!     println!("{:#?}", information);
//!     if let Some(information) = information {
//!         if information.sse4_2() {
//!              println!("SSE 4.2 Available");
//!         }
//!     }
//! }
//! ```


#[macro_use]
extern crate cfg_if;

use std::{fmt, slice, str};
use std::ops::Deref;

#[repr(u32)]
enum RequestType {
    BasicInformation                  = 0x00000000,
    VersionInformation                = 0x00000001,
    ThermalPowerManagementInformation = 0x00000006,
    StructuredExtendedInformation     = 0x00000007,
    ProcessorExtendedState            = 0x0000000D,
    ExtendedFunctionInformation       = 0x80000000,
    ExtendedProcessorSignature        = 0x80000001,
    BrandString1                      = 0x80000002,
    BrandString2                      = 0x80000003,
    BrandString3                      = 0x80000004,
    // reserved                       = 0x80000005,
    CacheLine                         = 0x80000006,
    TimeStampCounter                  = 0x80000007,
    PhysicalAddressSize               = 0x80000008,
}

fn cpuid(code: RequestType) -> (u32, u32, u32, u32) {
    cpuid_ext(code, 0x00000000)
}

cfg_if! {
    if #[cfg(any(target_arch = "x86_64", target_arch = "x86"))] {
        #[cfg(feature = "unstable")]
        fn cpuid_ext(code: RequestType, code2: u32) -> (u32, u32, u32, u32) {
            let res1;
            let res2;
            let res3;
            let res4;

            unsafe {
                asm!("cpuid"
                     : // output operands
                     "={eax}"(res1),
                     "={ebx}"(res2),
                     "={ecx}"(res3),
                     "={edx}"(res4)
                     : // input operands
                     "{eax}"(code as u32),
                     "{ecx}"(0 as u32)
                     : // clobbers
                     : // options
                     );
            }

            (res1, res2, res3, res4)
        }

        #[cfg(not(feature = "unstable"))]
        fn cpuid_ext(code: RequestType, code2: u32) -> (u32, u32, u32, u32) {
            extern {
                // This function name encodes an ABI compatibility
                // version. When we release a new major version of the
                // crate, this should be bumped to allow co-existing
                // installations. If we need to change this interface,
                // we should likely bump this version as well!
                fn __cupid_cpuid_shim_0_3(code: u32, code2: u32, output: *mut u32);
            }

            let mut ret = [0; 4];

            unsafe {
                __cupid_cpuid_shim_0_3(code as u32, code2, ret.as_mut_ptr());
            }<commit_msg>bugfix: ecx value ignored in unstable builds<commit_after>#![cfg_attr(feature = "unstable", feature(asm))]
#![cfg_attr(not(any(target_arch = "x86_64", target_arch = "x86")), allow(dead_code))]

//! ```
//! extern crate cupid;
//!
//! fn main() {
//!     let information = cupid::master();
//!     println!("{:#?}", information);
//!     if let Some(information) = information {
//!         if information.sse4_2() {
//!              println!("SSE 4.2 Available");
//!         }
//!     }
//! }
//! ```


#[macro_use]
extern crate cfg_if;

use std::{fmt, slice, str};
use std::ops::Deref;

#[repr(u32)]
enum RequestType {
    BasicInformation                  = 0x00000000,
    VersionInformation                = 0x00000001,
    ThermalPowerManagementInformation = 0x00000006,
    StructuredExtendedInformation     = 0x00000007,
    ProcessorExtendedState            = 0x0000000D,
    ExtendedFunctionInformation       = 0x80000000,
    ExtendedProcessorSignature        = 0x80000001,
    BrandString1                      = 0x80000002,
    BrandString2                      = 0x80000003,
    BrandString3                      = 0x80000004,
    // reserved                       = 0x80000005,
    CacheLine                         = 0x80000006,
    TimeStampCounter                  = 0x80000007,
    PhysicalAddressSize               = 0x80000008,
}

fn cpuid(code: RequestType) -> (u32, u32, u32, u32) {
    cpuid_ext(code, 0x00000000)
}

cfg_if! {
    if #[cfg(any(target_arch = "x86_64", target_arch = "x86"))] {
        #[cfg(feature = "unstable")]
        fn cpuid_ext(code: RequestType, code2: u32) -> (u32, u32, u32, u32) {
            let res1;
            let res2;
            let res3;
            let res4;

            unsafe {
                asm!("cpuid"
                     : // output operands
                     "={eax}"(res1),
                     "={ebx}"(res2),
                     "={ecx}"(res3),
                     "={edx}"(res4)
                     : // input operands
                     "{eax}"(code as u32),
                     "{ecx}"(code2 as u32)
                     : // clobbers
                     : // options
                     );
            }

            (res1, res2, res3, res4)
        }

        #[cfg(not(feature = "unstable"))]
        fn cpuid_ext(code: RequestType, code2: u32) -> (u32, u32, u32, u32) {
            extern {
                // This function name encodes an ABI compatibility
                // version. When we release a new major version of the
                // crate, this should be bumped to allow co-existing
                // installations. If we need to change this interface,
                // we should likely bump this version as well!
                fn __cupid_cpuid_shim_0_3(code: u32, code2: u32, output: *mut u32);
            }

            let mut ret = [0; 4];

            unsafe {
                __cupid_cpuid_shim_0_3(code as u32, code2, ret.as_mut_ptr());
            }
{'fraction_non_alphanumeric': 0.12375148129338073, 'fraction_numerical': 0.07381073302861012, 'mean_word_length': 1.4709326641572564, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 9, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 14, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '1110056', 'n_tokens_mistral': 2104, 'n_tokens_neox': 1735, 'n_words': 398}