/*********************************************************************** * GlobalAddAtomA (KERNEL32.@) * * Add a character string to the global atom table and return a unique * value identifying it. * * RETURNS * Success: The atom allocated to str. * Failure: 0. */ ATOM WINAPI GlobalAddAtomA( LPCSTR str /* [in] String to add */ ) { ATOM atom = 0; __TRY { if (!check_integral_atom( str, &atom )) { WCHAR buffer[MAX_ATOM_LEN]; DWORD len = MultiByteToWideChar( CP_ACP, 0, str, strlen(str), buffer, MAX_ATOM_LEN ); if (!len) SetLastError( ERROR_INVALID_PARAMETER ); else { NTSTATUS status = NtAddAtom( buffer, len * sizeof(WCHAR), &atom ); if (status) { SetLastError( RtlNtStatusToDosError( status ) ); atom = 0; } } } } __EXCEPT_PAGE_FAULT { SetLastError( ERROR_INVALID_PARAMETER ); atom = 0; } __ENDTRY return atom; }
/*********************************************************************** * GlobalAddAtomW (KERNEL32.@) * * Unicode version of GlobalAddAtomA. */ ATOM WINAPI GlobalAddAtomW( LPCWSTR str ) { ATOM atom = 0; NTSTATUS status; if (!check_integral_atom( str, &atom ) && (status = NtAddAtom( str, strlenW( str ) * sizeof(WCHAR), &atom ))) { SetLastError( RtlNtStatusToDosError( status ) ); atom = 0; } return atom; }
static NTSTATUS FASTCALL InitUserAtoms(VOID) { RegisterControlAtoms(); gpsi->atomSysClass[ICLS_MENU] = 32768; gpsi->atomSysClass[ICLS_DESKTOP] = 32769; gpsi->atomSysClass[ICLS_DIALOG] = 32770; gpsi->atomSysClass[ICLS_SWITCH] = 32771; gpsi->atomSysClass[ICLS_ICONTITLE] = 32772; gpsi->atomSysClass[ICLS_TOOLTIPS] = 32774; /* System Message Atom */ AtomMessage = IntAddGlobalAtom(L"Message", TRUE); gpsi->atomSysClass[ICLS_HWNDMESSAGE] = AtomMessage; /* System Context Help Id Atom */ gpsi->atomContextHelpIdProp = IntAddGlobalAtom(L"SysCH", TRUE); gpsi->atomIconSmProp = IntAddGlobalAtom(L"SysICS", TRUE); gpsi->atomIconProp = IntAddGlobalAtom(L"SysIC", TRUE); gpsi->atomFrostedWindowProp = IntAddGlobalAtom(L"SysFrostedWindow", TRUE); AtomDDETrack = IntAddGlobalAtom(L"SysDT", TRUE); AtomQOS = IntAddGlobalAtom(L"SysQOS", TRUE); /* * FIXME: AddPropW uses the global kernel atom table, thus leading to conflicts if we use * the win32k atom table for this one. What is the right thing to do ? */ // AtomWndObj = IntAddGlobalAtom(L"SysWNDO", TRUE); NtAddAtom(L"SysWNDO", 14, &AtomWndObj); AtomLayer = IntAddGlobalAtom(L"SysLayer", TRUE); AtomFlashWndState = IntAddGlobalAtom(L"FlashWState", TRUE); return STATUS_SUCCESS; }
ATOM WINAPI InternalAddAtom(BOOLEAN Local, BOOLEAN Unicode, LPCSTR AtomName) { NTSTATUS Status; ANSI_STRING AnsiString; UNICODE_STRING UnicodeString; PUNICODE_STRING AtomNameString; ATOM Atom = INVALID_ATOM; /* Check if it's an integer atom */ if ((ULONG_PTR)AtomName <= 0xFFFF) { /* Convert the name to an atom */ Atom = (ATOM)PtrToShort((PVOID)AtomName); if (Atom >= MAXINTATOM) { /* Fail, atom number too large */ BaseSetLastNTError(STATUS_INVALID_PARAMETER); return INVALID_ATOM; } /* Return it */ return Atom; } else { /* Check if this is a unicode atom */ if (Unicode) { /* Use a unicode string */ AtomNameString = &UnicodeString; RtlInitUnicodeString(AtomNameString, (LPWSTR)AtomName); Status = STATUS_SUCCESS; } else { /* Use an ansi string */ RtlInitAnsiString(&AnsiString, AtomName ); /* Check if we can abuse the TEB */ if (AnsiString.MaximumLength > 260) { /* We can't, allocate a new string */ AtomNameString = &UnicodeString; Status = RtlAnsiStringToUnicodeString(AtomNameString, &AnsiString, TRUE); } else { /* We can! Get the TEB String */ AtomNameString = &NtCurrentTeb()->StaticUnicodeString; /* Convert it into the TEB */ Status = RtlAnsiStringToUnicodeString(AtomNameString, &AnsiString, FALSE); } } /* Check for failure */ if (!NT_SUCCESS(Status)) { BaseSetLastNTError(Status); return Atom; } } /* Check if we're doing local add */ if (Local) { /* Do a local add */ Status = RtlAddAtomToAtomTable(InternalInitAtomTable(), AtomNameString->Buffer, &Atom); } else { /* Do a global add */ Status = NtAddAtom(AtomNameString->Buffer, AtomNameString->Length, &Atom); } /* Check for failure */ if (!NT_SUCCESS(Status)) BaseSetLastNTError(Status); /* Check if we were non-static ANSI */ if (!(Unicode) && (AtomNameString == &UnicodeString)) { /* Free the allocated buffer */ RtlFreeUnicodeString(AtomNameString); } /* Return the atom */ return Atom; }