Example #1
0
BOOL ValidateStringIdKeyW(
    LPCWSTR lpszDeviceStringId,
    LPCWSTR lpszDeviceStringKey,
    PBOOL pbWritable)
{
    NDAS_ID_KEY_INFO info;
    ::ZeroMemory(&info, sizeof(NDAS_ID_KEY_INFO));

    // check id length
    if (lpszDeviceStringId[NDAS_DEVICE_STRING_ID_LEN] != L'\0') {
        return FALSE;
    }

    // copy id
    for (DWORD i = 0; i < NDAS_DEVICE_STRING_ID_PARTS; ++i) {
        for (DWORD j = 0; j < NDAS_DEVICE_STRING_ID_PART_LEN; ++j) {
            info.serialNo[i][j] = static_cast<CHAR>(lpszDeviceStringId[i * NDAS_DEVICE_STRING_ID_PART_LEN + j]);
        }
    }

    if (NULL != lpszDeviceStringKey) {

        // check key length
        if (lpszDeviceStringKey[NDAS_DEVICE_STRING_KEY_LEN] != L'\0') {
            return FALSE;
        }

        // copy key
        for (DWORD i = 0; i < NDAS_DEVICE_STRING_KEY_LEN; ++i) {
            info.writeKey[i] = static_cast<CHAR>(lpszDeviceStringKey[i]);
        }
    }

    ::CopyMemory(info.key1, NDIDV1Key1, 8 * sizeof(CHAR));
    ::CopyMemory(info.key2, NDIDV1Key2, 8 * sizeof(CHAR));

    //
    // Only string id will be validated on its return and
    // write key is validated by info.bWritable
    //
    BOOL fSuccess = NdasIdKey_Decrypt(&info);

    if (NULL == lpszDeviceStringKey) {
        if (pbWritable) *pbWritable = FALSE;
        return fSuccess;
    } else {
        if (fSuccess && info.writable) {
            if (pbWritable) *pbWritable = TRUE;
            return TRUE;
        } else {
            if (pbWritable) *pbWritable = FALSE;
            return FALSE;
        }
    }
}
Example #2
0
BOOL ConvertStringIdToRealIdW(
    LPCWSTR lpszDeviceStringId,
    PNDAS_DEVICE_ID pDeviceId)
{
    _ASSERTE(!::IsBadStringPtrW(lpszDeviceStringId,NDAS_DEVICE_STRING_ID_LEN + 1));
    _ASSERTE(!::IsBadWritePtr(pDeviceId, sizeof(NDAS_DEVICE_ID)));

    NDAS_ID_KEY_INFO info;
    ::ZeroMemory(&info, sizeof(NDAS_ID_KEY_INFO));

    // check id length
    if (lpszDeviceStringId[NDAS_DEVICE_STRING_ID_LEN] != L'\0') {
        return FALSE;
    }

    // copy id
    for (DWORD i = 0; i < NDAS_DEVICE_STRING_ID_PARTS; ++i) {
        for (DWORD j = 0; j < NDAS_DEVICE_STRING_ID_PART_LEN; ++j) {
            info.serialNo[i][j] = static_cast<CHAR>(
                                      lpszDeviceStringId[i * NDAS_DEVICE_STRING_ID_PART_LEN + j]);
        }
    }

    // fill required keys
    ::CopyMemory(info.key1, NDIDV1Key1, 8 * sizeof(CHAR));
    ::CopyMemory(info.key2, NDIDV1Key2, 8 * sizeof(CHAR));

    // try decrypt
    if (!NdasIdKey_Decrypt(&info)) {
        return FALSE;
    }

    // fill the output
    ::CopyMemory( pDeviceId->Node, info.address, sizeof(BYTE) * 6);

    return TRUE;
}
Example #3
0
void CMainDialog::OnCmdParse(UINT wNotifyCode, int wID, HWND hWndCtl)
{
	NDAS_ID_KEY_INFO info = {0};

	for (int i = 0; i < RTL_NUMBER_OF(m_wndAddresses); ++i)
	{
		m_wndAddresses[i].SetWindowText(_T(""));
	}

	C_ASSERT(RTL_NUMBER_OF(m_wndKeys1) == RTL_NUMBER_OF(info.key1));

	for (int i = 0; i < RTL_NUMBER_OF(m_wndKeys1); ++i)
	{
		if (!pGetByteFromEdit(m_wndKeys1[i], info.key1[i]))
		{
			return;
		}
	}

	C_ASSERT(RTL_NUMBER_OF(m_wndKeys2) == RTL_NUMBER_OF(info.key2));

	for (int i = 0; i < RTL_NUMBER_OF(m_wndKeys2); ++i)
	{
		if (!pGetByteFromEdit(m_wndKeys2[i], info.key2[i]))
		{
			return;
		}
	}

	for (int i = 0; i < 4; ++i)
	{
		TCHAR part[6] = {0};
		m_wndNdasId[i].GetWindowText(part, 6);
		for (int j = 0; j < 5; ++j)
		{
			info.serialNo[i][j] = static_cast<char>(part[j]);
		}
	}

	if (!NdasIdKey_Decrypt(&info))
	{
		m_wndNdasId[0].SetFocus();
		m_wndNdasId[0].SetSel(0, -1);
		return;
	}

	for (int i = 0; i < RTL_NUMBER_OF(m_wndAddresses); ++i)
	{
		CString s = pBytesToString(&info.address[i], 1);
		m_wndAddresses[i].SetWindowText(s);
	}

	{
		CString s = pBytesToString(&info.vid, 1);
		m_wndVID.SetWindowText(s);
	}

	C_ASSERT(RTL_NUMBER_OF(m_wndReserved) == RTL_NUMBER_OF(info.reserved));

	for (int i = 0; i < RTL_NUMBER_OF(m_wndReserved); ++i)
	{
		CString s = pBytesToString(&info.reserved[i], 1);
		m_wndReserved[i].SetWindowText(s);
	}

	{
		CString s = pBytesToString(&info.random, 1);
		m_wndSeed.SetWindowText(s);
	}

	m_wndSerialNumberDigit.SetWindowText(pGetSNDigitString(info.address));
}
Example #4
0
// internal function
BOOL
WINAPI
pNdasIdStringToDeviceA(
	__in LPCSTR NdasId,
	__in_opt LPCSTR WriteKey,
	__out_opt NDAS_DEVICE_ID* DeviceID,
	__in_opt const NDASID_EXT_KEY* ExtKey,
	__out_opt NDASID_EXT_DATA* ExtData)
{
	// internal function validate parameters minimally.

	//
	// Decryption parameters:
	//
	// in: key1, key2, serialNo, writeKey
	// out: address, vid, random, reserved, writable
	//

	NDAS_ID_KEY_INFO ni = {0};

	//
	// input parameters
	//

	if (NULL == ExtKey)
	{
		ExtKey = &NDASID_EXT_KEY_DEFAULT;
	}

	CopyMemory(ni.serialNo, NdasId, sizeof(ni.serialNo));

	if (NULL != WriteKey && 0 != WriteKey[0])
	{
		CopyMemory(ni.writeKey, WriteKey, sizeof(ni.writeKey));
	}

	C_ASSERT_EQUALSIZE(ni.key1, ExtKey->Key1);
	CopyMemory(ni.key1, ExtKey->Key1, sizeof(ni.key1));

	C_ASSERT_EQUALSIZE(ni.key2, ExtKey->Key2);
	CopyMemory(ni.key2, ExtKey->Key2, sizeof(ni.key2));

	//
	// Decryption
	//

	if (!NdasIdKey_Decrypt(&ni))
	{
		return SetLastError(NDAS_ERROR_INVALID_ID_FORMAT), FALSE;
	}

	//
	// Is Write Key valid?
	//

	if (WriteKey && WriteKey[0] && !ni.writable)
	{
		return SetLastError(NDAS_ERROR_INVALID_ID_FORMAT), FALSE;
	}

#define NDASID_USE_SINGLE_MAPPING
#ifdef NDASID_USE_SINGLE_MAPPING

	//
	// NDAS ID Encryption - Decryption Mapping Problem
	//
	// For a given, AAAA1-BBBB2-CCCC3-DDDD4,
	// other IDs which has incremented values of last digit of any part
	// are treated as same, e.g. AAAA1-BBBB3-CCCC4-DDDD4 generates the
	// same value as above. So is the write key.
	//
	// To prevent such anomalies, we should regenerate a string ID with
	// a generated device ID and re-compare to test a validity of the
	// given string ID.
	//
	// This means, even though there can be more than one string IDs
	// which map to a device ID, we ratify only a single ID,
	// that is generated from the device ID.
	//

	{
		NDAS_DEVICE_ID compDeviceID;
		NDASID_EXT_DATA compExtData;

		C_ASSERT_EQUALSIZE(compDeviceID.Node, ni.address);
		CopyMemory(compDeviceID.Node, ni.address, sizeof(ni.address));

		compExtData.Seed = ni.random;
		compExtData.VID = ni.vid;
		C_ASSERT_EQUALSIZE(compExtData.Reserved, ni.reserved);
		CopyMemory(compExtData.Reserved, ni.reserved, sizeof(ni.reserved));

		CHAR newNdasId[NDAS_DEVICE_STRING_ID_LEN + 1] = {0};
		CHAR newWriteKey[NDAS_DEVICE_STRING_KEY_LEN + 1] = {0};

		BOOL success = NdasIdDeviceToStringExA(
			&compDeviceID, 
			newNdasId, 
			newWriteKey, 
			ExtKey, // constant
			&compExtData);

		if (!success)
		{
			_ASSERTE(FALSE); // should not fail!
			return FALSE;
		}

		//
		// We should compare both case-insensitively!
		// NdasIdDeviceToStringExA always returns capital letters
		// but lpszStringId may have mixed cases.
		//
		if (0 != lstrcmpiA(newNdasId, NdasId))
		{
			return SetLastError(NDAS_ERROR_INVALID_ID_FORMAT), FALSE;
		}

		// check write key also, if given
		if (WriteKey && 
			WriteKey [0] && 
			0 != lstrcmpiA(newWriteKey, WriteKey ))
		{
			return SetLastError(NDAS_ERROR_INVALID_ID_FORMAT), FALSE;
		}
	}

#endif

	//
	// Copy outputs
	//

	if (NULL != DeviceID)
	{
		C_ASSERT_EQUALSIZE(DeviceID->Node, ni.address);
		CopyMemory(DeviceID->Node, ni.address, sizeof(ni.address));
	}

	if (NULL != ExtData)
	{
		ExtData->Seed = ni.random;
		ExtData->VID = ni.vid;
		C_ASSERT_EQUALSIZE(ni.reserved, ExtData->Reserved);
		CopyMemory(ExtData->Reserved, ni.reserved, sizeof(ni.reserved));
	}

	return TRUE;
}