test: uilist.c File Reference

Main Page | Class Hierarchy | Class List | File List | Class Members | File Members

# uilist.c File Reference

`#include <nt.h>`
`#include <ntrtl.h>`
`#include <nturtl.h>`
`#include <windows.h>`
`#include <wchar.h>`

Go to the source code of this file.

## Defines

#define | IS_DELIMITER(c, _BlankOk)
#define | ILLEGAL_NAME_CHARS

## Functions

ULONG | NextElement (IN OUT PWSTR *InputBuffer, IN OUT PULONG InputBufferLength, OUT PWSTR OutputBuffer, IN ULONG OutputBufferLength, IN BOOLEAN BlankIsDelimiter)
BOOLEAN | ValidateName (IN PWSTR Name, IN ULONG Length)
NTSTATUS | RtlConvertUiListToApiList (IN PUNICODE_STRING UiList OPTIONAL, OUT PUNICODE_STRING ApiList, IN BOOLEAN BlankIsDelimiter)

## Define Documentation

#define ILLEGAL_NAME_CHARS

Value:

    L"\001\002\003\004\005\006\007" \
                                L"\010\011\012\013\014\015\016\017" \
                                L"\020\021\022\023\024\025\026\027" \
                                L"\030\031\032\033\034\035\036\037" \
                                L"\"/\\[]:|<>+=;,?*"

Definition at line 264 of file uilist.c.

Referenced by ValidateName().

#define IS_DELIMITER | ( | c,
|  | _BlankOk |  | ) |

Value:

    (((c) == L' ' && (_BlankOk)) || \
        ((c) == L'\t') || ((c) == L',') || ((c) == L';'))

Definition at line 41 of file uilist.c.

Referenced by NextElement().

## Function Documentation

ULONG NextElement | ( | IN OUT PWSTR * | InputBuffer,
|  | IN OUT PULONG | InputBufferLength,
|  | OUT PWSTR | OutputBuffer,
|  | IN ULONG | OutputBufferLength,
|  | IN BOOLEAN | BlankIsDelimiter
| ) | `[static]`

Definition at line 200 of file uilist.c.

References IS_DELIMITER, and L.

Referenced by RtlConvertUiListToApiList().

    00210                    :
    00211
    00212     Locates the next (non-delimter) element in a string and extracts it to a
    00213     buffer. Delimiters are the set [\t,;]
    00214
    00215 Arguments:
    00216
    00217     InputBuffer         - pointer to pointer to input buffer including delimiters
    00218                           Updated on successful return
    00219     InputBufferLength   - pointer to length of characters in InputBuffer.
    00220                           Updated on successful return
    00221     OutputBuffer        - pointer to buffer where next element is copied
    00222     OutputBufferLength  - size of OutputBuffer (in bytes)
    00223     BlankIsDelimiter    - TRUE indicates blank should be considered a delimiter
    00224               character.
    00225
    00226 Return Value:
    00227
    00228     ULONG
    00229                            -1 = error - extracted element breaks OutputBuffer
    00230                             0 = no element extracted (buffer is empty or all
    00231                                 delimiters)
    00232         1..OutputBufferLength = OutputBuffer contains extracted element
    00233
    00234 --*/
    00235
    00236 {
    00237     ULONG elementLength = 0;
    00238     ULONG inputLength = *InputBufferLength;
    00239     PWSTR input = *InputBuffer;
    00240
    00241     while (IS_DELIMITER(*input, BlankIsDelimiter) && inputLength) {
    00242         ++input;
    00243         inputLength -= sizeof(*input);
    00244     }
    00245     while (!IS_DELIMITER(*input, BlankIsDelimiter) && inputLength) {
    00246         if (!OutputBufferLength) {
    00247             return (ULONG)-1L;
    00248         }
    00249         *OutputBuffer++ = *input++;
    00250         OutputBufferLength -= sizeof(*input);
    00251         elementLength += sizeof(*input);
    00252         inputLength -= sizeof(*input);
    00253     }
    00254     *InputBuffer = input;
    00255     *InputBufferLength = inputLength;
    00256     return elementLength;
    00257 }

NTSTATUS RtlConvertUiListToApiList | ( | IN PUNICODE_STRING UiList | OPTIONAL,
|  | OUT PUNICODE_STRING | ApiList,
|  | IN BOOLEAN | BlankIsDelimiter
| ) |

Definition at line 72 of file uilist.c.

References EXCEPTION_EXECUTE_HANDLER, FALSE, L, NextElement(), NT_SUCCESS, NTSTATUS(), NULL, RtlAllocateHeap, RtlFreeHeap, RtlInitUnicodeString(), TRUE, USHORT, and ValidateName().

    00080                    :
    00081
    00082     Converts a list of workstation names in UI/Service format into a list of
    00083     canonicalized names in API list format. UI/Service list format allows
    00084     multiple delimiters, leading and trailing delimiters. Delimiters are the
    00085     set "\t,;". API list format has no leading or trailing delimiters and
    00086     elements are delimited by a single comma character.
    00087
    00088     For each name parsed from UiList, the name is canonicalized (which checks
    00089     the character set and name length) as a workstation name. If this fails,
    00090     an error is returned. No information is returned as to which element
    00091     failed canonicalization: the list should be discarded and a new one re-input
    00092
    00093 Arguments:
    00094
    00095     UiList  - The list to canonicalize in UI/Service list format
    00096     ApiList - The place to store the canonicalized version of the list in
    00097               API list format.  The list will have a trailing zero character.
    00098     BlankIsDelimiter - TRUE indicates blank should be considered a delimiter
    00099               character.
    00100
    00101 Return Value:
    00102
    00103     NTSTATUS
    00104         Success = STATUS_SUCCESS
    00105                     List converted ok
    00106
    00107         Failure = STATUS_INVALID_PARAMETER
    00108                     UiList parameter is in error
    00109
    00110                   STATUS_INVALID_COMPUTER_NAME
    00111                     A name parsed from UiList has an incorrect format for a
    00112                     computer (aka workstation) name
    00113 --*/
    00114
    00115 {
    00116     NTSTATUS status = STATUS_SUCCESS;
    00117     ULONG inLen;
    00118     PWSTR input;
    00119     PWSTR buffer;
    00120     PWSTR output;
    00121     ULONG cLen;
    00122     ULONG len;
    00123     ULONG outLen = 0;
    00124     WCHAR element[MAX_COMPUTERNAME_LENGTH+1];
    00125     BOOLEAN firstElement = TRUE;
    00126     BOOLEAN ok;
    00127
    00128     try {
    00129         if (ARGUMENT_PRESENT(UiList)) {
    00130             inLen = UiList->MaximumLength;  // read memory test
    00131             inLen = UiList->Length;
    00132             input = UiList->Buffer;
    00133             if (inLen & sizeof(WCHAR)-1) {
    00134                 status = STATUS_INVALID_PARAMETER;
    00135             }
    00136         }
    00137         RtlInitUnicodeString(ApiList, NULL);
    00138     } except (EXCEPTION_EXECUTE_HANDLER) {
    00139         status = STATUS_ACCESS_VIOLATION;
    00140     }
    00141     if (NT_SUCCESS(status) && ARGUMENT_PRESENT(UiList) && inLen) {
    00142         buffer = RtlAllocateHeap(RtlProcessHeap(), 0, inLen + sizeof(WCHAR));
    00143         if (buffer == NULL) {
    00144             status = STATUS_NO_MEMORY;
    00145         } else {
    00146             ApiList->Buffer = buffer;
    00147             ApiList->MaximumLength = (USHORT)inLen + sizeof(WCHAR);
    00148             output = buffer;
    00149             ok = TRUE;
    00150             while (len = NextElement(&input,
    00151                                      &inLen,
    00152                                      element,
    00153                                      sizeof(element) - sizeof(element[0]),
    00154                                      BlankIsDelimiter )) {
    00155                 if (len == (ULONG)-1L) {
    00156                     ok = FALSE;
    00157                 } else {
    00158                     cLen = len/sizeof(WCHAR);
    00159                     element[cLen] = 0;
    00160                     ok = ValidateName(element, cLen);
    00161                 }
    00162                 if (ok) {
    00163                     if (!firstElement) {
    00164                         *output++ = L',';
    00165
    00166                         //
    00167                         // BUGBUG sizeof(L',') returns 4, not 2!!
    00168                         //
    00169
    00170 //                        outLen += sizeof(L',');
    00171                         outLen += sizeof(WCHAR);
    00172                     } else {
    00173                         firstElement = FALSE;
    00174                     }
    00175                     wcscpy(output, element);
    00176                     outLen += len;
    00177                     output += cLen;
    00178                 } else {
    00179                     RtlFreeHeap(RtlProcessHeap(), 0, buffer);
    00180                     ApiList->Buffer = NULL;
    00181                     status = STATUS_INVALID_COMPUTER_NAME;
    00182                     break;
    00183                 }
    00184             }
    00185         }
    00186         if (NT_SUCCESS(status)) {
    00187             ApiList->Length = (USHORT)outLen;
    00188             if (!outLen) {
    00189                 ApiList->MaximumLength = 0;
    00190                 ApiList->Buffer = NULL;
    00191                 RtlFreeHeap(RtlProcessHeap(), 0, buffer);
    00192             }
    00193         }
    00194     }
    00195     return status;
    00196 }

BOOLEAN ValidateName | ( | IN PWSTR | Name,
|  | IN ULONG | Length
| ) | `[static]`

Definition at line 272 of file uilist.c.

References FALSE, ILLEGAL_NAME_CHARS, and Name.

Referenced by RtlConvertUiListToApiList().

    00279                    :
    00280
    00281     Determines whether a computer name is valid or not
    00282
    00283 Arguments:
    00284
    00285     Name    - pointer to zero terminated wide-character computer name
    00286     Length  - of Name in characters, excluding zero-terminator
    00287
    00288 Return Value:
    00289
    00290     BOOLEAN
    00291         TRUE    Name is valid computer name
    00292         FALSE   Name is not valid computer name
    00293
    00294 --*/
    00295
    00296 {
    00297     if (Length > MAX_COMPUTERNAME_LENGTH || Length < 1) {
    00298         return FALSE;
    00299     }
    00300
    00301     //
    00302     // Don't allow leading or trailing blanks in the computername.
    00303     //
    00304
    00305     if ( Name[0] == ' ' || Name[Length-1] == ' ' ) {
    00306         return(FALSE);
    00307     }
    00308
    00309     return (BOOLEAN)((ULONG)wcscspn(Name, ILLEGAL_NAME_CHARS) == Length);
    00310 }
    }