(file) Return to Options.c CVS log (file) (dir) Up to [OMI] / omi / miapi

   1 krisbash 1.1 #include "Options.h"
   2              #include <pal/strings.h>
   3              #include <pal/encrypt.h>
   4              
   5              extern MI_DestinationOptionsFT g_destinationOptionsFT;
   6              extern MI_OperationOptionsFT g_operationOptionsFT;
   7              extern MI_SubscriptionDeliveryOptionsFT g_subscriptionDeliveryOptionsFT;
   8              
   9              
  10              
  11              MI_Result GenericOptions_Create(
  12                  _Out_ struct _GenericOptions_Handle *options,
  13                  _In_ void *ft)
  14              {
  15                  Batch *batch;
  16                  struct _GenericOptions *genericOptions;
  17              
  18                  batch = Batch_New(BATCH_MAX_PAGES);
  19                  if (batch == NULL)
  20                      return MI_RESULT_SERVER_LIMITS_EXCEEDED;
  21              
  22 krisbash 1.1     genericOptions = Batch_Get(batch, sizeof(*genericOptions));
  23                  if (genericOptions == NULL)
  24                  {
  25                      Batch_Delete(batch);
  26                      return MI_RESULT_SERVER_LIMITS_EXCEEDED;
  27                  }
  28                  
  29                  genericOptions->batch = batch;
  30                  genericOptions->credentialInstance = NULL;
  31                  genericOptions->optionsInstance = NULL;
  32                  genericOptions->referenceCount = 1;
  33              
  34                  options->reserved1 = 0;
  35                  options->genericOptions = genericOptions;
  36                  options->ft = ft;
  37              
  38                  return MI_RESULT_OK;
  39              }
  40              
  41              
  42              MI_Result MI_CALL GenericOptions_Delete(
  43 krisbash 1.1     _Inout_ struct _GenericOptions_Handle *options)
  44              {
  45                  if (options && options->genericOptions)
  46                  {
  47                      if (Atomic_Dec(&options->genericOptions->referenceCount) == 0)
  48                      {
  49                          if (options->genericOptions->batch)
  50                              Batch_Delete(options->genericOptions->batch);
  51              
  52                          options->genericOptions = NULL;
  53                          options->reserved1 = 0;
  54                          options->ft = NULL;
  55                      }
  56                      return MI_RESULT_OK;
  57                  }
  58                  return MI_RESULT_INVALID_PARAMETER;
  59              }
  60              
  61              MI_Result MI_CALL GenericOptions_Clone(
  62                  _In_ const struct _GenericOptions_Handle* options,
  63                  _Out_ struct _GenericOptions_Handle* newOptions)
  64 krisbash 1.1 {
  65                  if (options && newOptions)
  66                  {
  67                      struct _GenericOptions *genericOptions =  options->genericOptions;
  68                      MI_Result miResult;
  69                      miResult = GenericOptions_Create(newOptions, options->ft);
  70                      if (miResult == MI_RESULT_OK)
  71                      {
  72                          if (genericOptions->optionsInstance)
  73                          {
  74                              miResult = Instance_Clone(genericOptions->optionsInstance, &newOptions->genericOptions->optionsInstance, newOptions->genericOptions->batch);
  75                              if (miResult != MI_RESULT_OK)
  76                              {
  77                                  GenericOptions_Delete(newOptions);
  78                                  return miResult;
  79                              }
  80                          }
  81                          if (genericOptions->credentialInstance)
  82                          {
  83                              miResult = Instance_Clone(genericOptions->credentialInstance, &newOptions->genericOptions->credentialInstance, newOptions->genericOptions->batch);
  84                              if (miResult != MI_RESULT_OK)
  85 krisbash 1.1                 {
  86                                  GenericOptions_Delete(newOptions);
  87                              }
  88                          }
  89                      }
  90                      return miResult;
  91                  }
  92                  else
  93                      return MI_RESULT_INVALID_PARAMETER;
  94              }
  95              
  96              MI_INLINE MI_Result _AddOrSetElement(_Inout_ MI_Instance *optionsInstance,
  97                  _In_z_ const MI_Char* optionName,
  98                  _In_opt_ const MI_Value* value,
  99                  MI_Type type,
 100                  MI_Uint32 flags)
 101              {
 102                  MI_Result miResult;
 103              
 104                  miResult = MI_Instance_AddElement(optionsInstance, optionName, value, type, flags);
 105                  if (miResult == MI_RESULT_ALREADY_EXISTS)
 106 krisbash 1.1     {
 107                      miResult = MI_Instance_SetElement(optionsInstance, optionName, value, type, flags);
 108                  }
 109                  return miResult;
 110              }
 111              
 112              MI_INLINE MI_Result _AddOrSetCustomElement(_Inout_ MI_Instance *optionsInstance, _Inout_ Batch *batch,
 113                  _In_z_ const MI_Char* optionName,
 114                  _In_opt_ const MI_Value* value,
 115                  MI_Type type,
 116                  MI_Boolean mustUnderstand,
 117                  MI_Uint32 flags)
 118              {
 119                  MI_Instance *elem;
 120                  MI_Result miResult;
 121                  MI_Value tmpValue;
 122                  MI_Type tmpType;
 123              
 124                  miResult = MI_Instance_GetElement(optionsInstance, optionName, &tmpValue, &tmpType, NULL, NULL);
 125                  if (miResult == MI_RESULT_NO_SUCH_PROPERTY)
 126                  {
 127 krisbash 1.1         miResult = Instance_NewDynamic(&elem, MI_T("_OMI_CustomOptionValue"), MI_FLAG_CLASS, batch);
 128                      if (miResult != MI_RESULT_OK)
 129                          return miResult;
 130              
 131                      miResult = MI_Instance_AddElement(elem, MI_T("value"), value, type, 0);
 132                      if (miResult != MI_RESULT_OK)
 133                          return miResult;
 134              
 135                      tmpValue.boolean = mustUnderstand;
 136                      miResult = MI_Instance_AddElement(elem, MI_T("mustUnderstand"), &tmpValue, MI_BOOLEAN, 0);
 137                      if (miResult != MI_RESULT_OK)
 138                          return miResult;
 139              
 140                      tmpValue.instance = elem;
 141                      miResult = MI_Instance_AddElement(optionsInstance, optionName, &tmpValue, MI_INSTANCE, MI_FLAG_BORROW);
 142                      return miResult;
 143                  }
 144                  else if (miResult != MI_RESULT_OK)
 145                      return miResult;
 146                  else
 147                  {
 148 krisbash 1.1         if (tmpType != MI_INSTANCE)
 149                          return MI_RESULT_INVALID_PARAMETER;
 150                      
 151                      elem = tmpValue.instance;
 152              
 153                      /* SetElement will fail if the type is changed */
 154                      miResult = MI_Instance_SetElement(elem, MI_T("value"), value, type, 0);
 155                      if (miResult != MI_RESULT_OK)
 156                          return miResult;
 157              
 158                      tmpValue.boolean = mustUnderstand;
 159                      miResult = MI_Instance_SetElement(elem, MI_T("mustUnderstand"), &tmpValue, MI_BOOLEAN, 0);
 160                      return miResult;
 161                  }
 162              }
 163              MI_INLINE MI_Result _AddOrSetGenericOption(_Inout_ struct _GenericOptions *genericOptions,
 164                  _In_z_ const MI_Char* optionName,
 165                  _In_opt_ const MI_Value* optionValue,
 166                  MI_Type optionType,
 167                  MI_Uint32 elementFlags)
 168              {
 169 krisbash 1.1     MI_Result miResult;
 170                  if ((genericOptions == NULL) || (genericOptions->batch == NULL))
 171                  {
 172                      return MI_RESULT_INVALID_PARAMETER;
 173                  }
 174                  if (genericOptions->optionsInstance == NULL)
 175                  {
 176                      miResult = Instance_NewDynamic(&genericOptions->optionsInstance, MI_T("_OMI_OptionSet"), MI_FLAG_CLASS, genericOptions->batch);
 177                      if (miResult != MI_RESULT_OK)
 178                      {
 179                          return miResult;
 180                      }
 181                  }
 182              
 183                  return _AddOrSetElement(genericOptions->optionsInstance, optionName, optionValue, optionType, elementFlags);
 184              }
 185              
 186              MI_INLINE MI_Result _AddOrSetGenericCustomOption(_Inout_ struct _GenericOptions *genericOptions,
 187                  _In_z_ const MI_Char* optionName,
 188                  _In_opt_ const MI_Value* optionValue,
 189                  MI_Type optionType,
 190 krisbash 1.1     MI_Boolean mustUnderstand,
 191                  MI_Uint32 optionFlags)
 192              {
 193                  MI_Result miResult;
 194                  if ((genericOptions == NULL) || (genericOptions->batch == NULL))
 195                  {
 196                      return MI_RESULT_INVALID_PARAMETER;
 197                  }
 198                  if (genericOptions->optionsInstance == NULL)
 199                  {
 200                      miResult = Instance_NewDynamic(&genericOptions->optionsInstance, MI_T("_OMI_OptionSet"), MI_FLAG_CLASS, genericOptions->batch);
 201                      if (miResult != MI_RESULT_OK)
 202                      {
 203                          return miResult;
 204                      }
 205                  }
 206              
 207                  return _AddOrSetCustomElement(genericOptions->optionsInstance, genericOptions->batch, optionName, optionValue, optionType, mustUnderstand, optionFlags);
 208              }
 209              
 210              MI_INLINE MI_Result _GetGenericOptionsValue(
 211 krisbash 1.1     _In_   const struct _GenericOptions_Handle *options,
 212                  _In_z_ const MI_Char *optionName,
 213                  _Out_opt_ MI_Type *type,
 214                  _Out_opt_ MI_Value *value,
 215                  _Out_opt_ MI_Uint32 *index)
 216              {
 217                  if ((options == NULL) || (optionName == NULL) || (value == NULL))
 218                      return MI_RESULT_INVALID_PARAMETER;
 219              
 220                  {
 221                      struct _GenericOptions *genericOptions = options->genericOptions;
 222                      if (genericOptions->optionsInstance)
 223                      {
 224                          return MI_Instance_GetElement(genericOptions->optionsInstance, optionName, value, type, 0, index);
 225                      }
 226                      else
 227                          return MI_RESULT_NO_SUCH_PROPERTY;
 228                  }
 229              }
 230              
 231              
 232 krisbash 1.1 MI_Result MI_CALL GenericOptions_SetString(
 233                  _Inout_   struct _GenericOptions_Handle *options,
 234                  _In_z_ const MI_Char *optionName,
 235                  _In_z_ const MI_Char *value,
 236                          MI_Uint32 flags)
 237              {
 238                  if ((options == NULL) || (optionName == NULL) || (value == NULL) || flags)
 239                      return MI_RESULT_INVALID_PARAMETER;
 240              
 241                  {
 242                      struct _GenericOptions *genericOptions = options->genericOptions;
 243                      MI_Value _value;
 244              
 245                      _value.string = (MI_Char*)value;
 246              
 247                      return _AddOrSetGenericOption(genericOptions, optionName, &_value, MI_STRING, 0);
 248                  }
 249              }
 250              
 251              MI_Result MI_CALL GenericOptions_EnableDisableChannel(
 252                  _Inout_   struct _GenericOptions_Handle *options,
 253 krisbash 1.1     _In_z_ const MI_Char *optionName,
 254                  _In_   MI_Uint32 value,
 255                          MI_Uint32 flags)
 256              {
 257                  MI_Type tmpType;
 258                  MI_Value tmpValue;
 259                  MI_Result miResult;
 260                  MI_Uint32 index;
 261              
 262                  /* Deal with channel enabling/disabling */
 263                  miResult = _GetGenericOptionsValue(options, optionName, &tmpType, &tmpValue, NULL);
 264                  if (miResult == MI_RESULT_NO_SUCH_PROPERTY)
 265                  {
 266                      /* Not there so we need to add it */
 267                      miResult = MI_RESULT_OK;
 268                      tmpValue.uint32a.data = NULL;
 269                      tmpValue.uint32a.size = 0;
 270                      tmpType = MI_UINT32A;
 271                  }
 272                  else if (miResult != MI_RESULT_OK)
 273                      return miResult;
 274 krisbash 1.1     else if (tmpType != MI_UINT32A)
 275                      return MI_RESULT_INVALID_PARAMETER;
 276              
 277                  for (index = 0; index != tmpValue.uint32a.size ; index++)
 278                  {
 279                      if (tmpValue.uint32a.data[index] == value)
 280                      {
 281                          if (flags == 0)
 282                          {
 283                              /* Already there */
 284                              return MI_RESULT_OK;
 285                          }
 286                          else
 287                          {
 288                              /* need to remove it */
 289                              for (; index+1 != tmpValue.uint32a.size; index++)
 290                              {
 291                                  tmpValue.uint32a.data[index] = tmpValue.uint32a.data[index+1];
 292                              }
 293                              tmpValue.uint32a.size --;
 294              
 295 krisbash 1.1                 return _AddOrSetGenericOption(options->genericOptions, optionName, &tmpValue, tmpType, MI_FLAG_BORROW);
 296                          }
 297                      }
 298                  }
 299                  /* Not there */
 300                  if (flags == 1)
 301                  {
 302                      /* Great, it is not there and we are disabling it */
 303                      return MI_RESULT_OK;
 304                  }
 305              
 306                  /* We need to add it. Make sure buffer is big enough */
 307                  if ((tmpValue.uint32a.size % 10) == 0)
 308                  {
 309                      /* Need to grow it */
 310                      void *tmpBuff = Batch_Get(options->genericOptions->batch, (tmpValue.uint32a.size+10)*sizeof(MI_Uint32));
 311                      if (tmpBuff == NULL)
 312                          return MI_RESULT_SERVER_LIMITS_EXCEEDED;
 313                      if (tmpValue.uint32a.data)
 314                      {
 315                          memcpy(tmpBuff, tmpValue.uint32a.data, tmpValue.uint32a.size*sizeof(MI_Uint32));
 316 krisbash 1.1             Batch_Put(options->genericOptions->batch, tmpValue.uint32a.data);
 317                      }
 318                      tmpValue.uint32a.data = tmpBuff;
 319                  }
 320              
 321                  tmpValue.uint32a.data[tmpValue.uint32a.size] = value;
 322                  tmpValue.uint32a.size++;
 323              
 324                  return _AddOrSetGenericOption(options->genericOptions, optionName, &tmpValue, tmpType, MI_FLAG_BORROW);
 325              }
 326              
 327              MI_Result MI_CALL GenericOptions_SetNumber(
 328                  _Inout_   struct _GenericOptions_Handle *options,
 329                  _In_z_ const MI_Char *optionName,
 330                  _In_   MI_Uint32 value,
 331                          MI_Uint32 flags)
 332              {
 333                  if ((options == NULL) || (optionName == NULL))
 334                      return MI_RESULT_INVALID_PARAMETER;
 335              
 336                  if ((Tcscmp(optionName, MI_T("__MI_OPERATIONOPTIONS_CHANNEL")) == 0) && (options->ft == &g_operationOptionsFT))
 337 krisbash 1.1     {
 338                      return GenericOptions_EnableDisableChannel(options, optionName, value, flags);
 339                  }
 340                  else
 341                  {
 342                      struct _GenericOptions *genericOptions = options->genericOptions;
 343                      MI_Value _value;
 344              
 345                      if (flags != 0)
 346                          return MI_RESULT_INVALID_PARAMETER;
 347              
 348                      _value.uint32 = value;
 349              
 350                      return _AddOrSetGenericOption(genericOptions, optionName, &_value, MI_UINT32, 0);
 351                  }
 352              }
 353              
 354              MI_Result MI_CALL GenericOptions_SetInterval(
 355                  _Inout_   struct _GenericOptions_Handle *options,
 356                  _In_z_ const MI_Char *optionName,
 357                  _In_   const MI_Interval *value,
 358 krisbash 1.1             MI_Uint32 flags)
 359              {
 360                  if ((options == NULL) || (optionName == NULL) || (value == NULL) || flags)
 361                      return MI_RESULT_INVALID_PARAMETER;
 362              
 363                  {
 364                      struct _GenericOptions *genericOptions = options->genericOptions;
 365                      MI_Value _value;
 366              
 367                      _value.datetime.isTimestamp = MI_FALSE;
 368                      _value.datetime.u.interval = *value;
 369              
 370                      return _AddOrSetGenericOption(genericOptions, optionName, &_value, MI_DATETIME, 0);
 371                  }
 372              }
 373              MI_Result MI_CALL GenericOptions_SetDateTime(
 374                  _Inout_   struct _GenericOptions_Handle *options,
 375                  _In_z_ const MI_Char *optionName,
 376                  _In_   const MI_Datetime *value,
 377                          MI_Uint32 flags)
 378              {
 379 krisbash 1.1     if ((options == NULL) || (optionName == NULL) || (value == NULL) || flags)
 380                      return MI_RESULT_INVALID_PARAMETER;
 381              
 382                  {
 383                      struct _GenericOptions *genericOptions = options->genericOptions;
 384                      MI_Value _value;
 385              
 386                      _value.datetime = *value;
 387              
 388                      return _AddOrSetGenericOption(genericOptions, optionName, &_value, MI_DATETIME, 0);
 389                  }
 390              }
 391              
 392              MI_Result MI_CALL GenericOptions_SetCustomOption(
 393                  _Inout_   struct _GenericOptions_Handle *options,
 394                  _In_z_ const MI_Char *optionName,
 395                  _In_   MI_Type valueType,
 396                  _In_   const MI_Value *value,
 397                          MI_Boolean mustComply,
 398                          MI_Uint32 flags)
 399              {
 400 krisbash 1.1     if ((options == NULL) || (optionName == NULL) || (value == NULL) || flags)
 401                      return MI_RESULT_INVALID_PARAMETER;
 402              
 403                  {
 404                      struct _GenericOptions *genericOptions = options->genericOptions;
 405              
 406                      /* TODO! What about mustComply */
 407                      return _AddOrSetGenericCustomOption(genericOptions, optionName, value, valueType, mustComply, 0);
 408                  }
 409              }
 410              
 411              
 412              MI_Result MI_CALL GenericOptions_GetString(
 413                  _In_   const struct _GenericOptions_Handle *options,
 414                  _In_z_ const MI_Char *optionName,
 415                  _Outptr_result_z_ const MI_Char **value,
 416                  _Out_opt_ MI_Uint32 *index,
 417                  _Out_opt_ MI_Uint32 *flags)
 418              {
 419                  MI_Result miResult;
 420                  MI_Value tmpValue;
 421 krisbash 1.1     MI_Type type;
 422                  
 423                  if ((options == NULL) || (optionName == NULL) || (value == NULL))
 424                      return MI_RESULT_INVALID_PARAMETER;
 425              
 426                  miResult = _GetGenericOptionsValue(options, optionName, &type, &tmpValue, index);
 427                  if (miResult == MI_RESULT_OK)
 428                  {
 429                      if (type != MI_STRING)
 430                          return MI_RESULT_TYPE_MISMATCH;
 431                      
 432                      if (value)
 433                          *value = tmpValue.string;
 434                      if (flags)
 435                          *flags = 0;
 436                  }
 437                  return miResult;
 438              }
 439              
 440              MI_Result MI_CALL GenericOptions_GetNumber(
 441                  _In_   const struct _GenericOptions_Handle *options,
 442 krisbash 1.1     _In_z_ const MI_Char *optionName,
 443                  _Out_ MI_Uint32 *value,
 444                  _Out_opt_ MI_Uint32 *index,
 445                  _Out_opt_ MI_Uint32 *flags)
 446              {
 447                  MI_Result miResult;
 448                  MI_Value tmpValue;
 449                  MI_Type type;
 450              
 451                  if ((options == NULL) || (optionName == NULL) || (value == NULL))
 452                      return MI_RESULT_INVALID_PARAMETER;
 453              
 454                  miResult = _GetGenericOptionsValue(options, optionName, &type, &tmpValue, index);
 455                  if (miResult == MI_RESULT_OK)
 456                  {
 457                      if (type != MI_UINT32)
 458                          return MI_RESULT_TYPE_MISMATCH;
 459                      
 460                      if (value)
 461                          *value = tmpValue.uint32;
 462                      if (flags)
 463 krisbash 1.1             *flags = 0;
 464                  }
 465              
 466                  return miResult;
 467              }
 468              
 469              
 470              MI_Result MI_CALL GenericOptions_GetInterval(
 471                  _In_   const struct _GenericOptions_Handle *options,
 472                  _In_z_ const MI_Char *optionName,
 473                  _Out_ MI_Interval *value,
 474                  _Out_opt_ MI_Uint32 *index,
 475                  _Out_opt_ MI_Uint32 *flags)
 476              {
 477                  MI_Result miResult;
 478                  MI_Value tmpValue;
 479                  MI_Type type;
 480              
 481                  if ((options == NULL) || (optionName == NULL) || (value == NULL))
 482                      return MI_RESULT_INVALID_PARAMETER;
 483              
 484 krisbash 1.1     miResult = _GetGenericOptionsValue(options, optionName, &type, &tmpValue, index);
 485                  if (miResult == MI_RESULT_OK)
 486                  {
 487                      if (type != MI_DATETIME)
 488                          return MI_RESULT_TYPE_MISMATCH;
 489                      
 490                      if (value)
 491                      {
 492                          if (tmpValue.datetime.isTimestamp == MI_TRUE)
 493                              miResult = MI_RESULT_TYPE_MISMATCH;
 494                          else
 495                              *value = tmpValue.datetime.u.interval;
 496                      }
 497                      if (flags)
 498                          *flags = 0;
 499                  }
 500                  return miResult;
 501              }
 502              
 503              MI_Result MI_CALL GenericOptions_GetDateTime(
 504                  _In_   const struct _GenericOptions_Handle *options,
 505 krisbash 1.1     _In_z_ const MI_Char *optionName,
 506                  _Out_ MI_Datetime *value,
 507                  _Out_opt_ MI_Uint32 *index,
 508                  _Out_opt_ MI_Uint32 *flags)
 509              {
 510                  MI_Result miResult;
 511                  MI_Value tmpValue;
 512                  MI_Type type;
 513              
 514                  if ((options == NULL) || (optionName == NULL) || (value == NULL))
 515                      return MI_RESULT_INVALID_PARAMETER;
 516              
 517                  miResult = _GetGenericOptionsValue(options, optionName, &type, &tmpValue, index);
 518                  if (miResult == MI_RESULT_OK)
 519                  {
 520                      if (type != MI_DATETIME)
 521                          return MI_RESULT_TYPE_MISMATCH;
 522                      
 523                      if (value)
 524                      {
 525                          *value = tmpValue.datetime;
 526 krisbash 1.1         }
 527                      if (flags)
 528                          *flags = 0;
 529                  }
 530                  return miResult;
 531              }
 532              
 533              MI_Result MI_CALL GenericOptions_GetOption(
 534                  _In_   const struct _GenericOptions_Handle *options,
 535                  _In_z_ const MI_Char *optionName,
 536                  _Out_ MI_Value *value,
 537                  _Out_ MI_Type *type,
 538                  _Out_opt_ MI_Uint32 *index,
 539                  _Out_opt_ MI_Uint32 *flags)
 540              {
 541                  if ((options == NULL) || (optionName == NULL) || (value == NULL) || (type == NULL))
 542                      return MI_RESULT_INVALID_PARAMETER;
 543              
 544                  if (flags)
 545                      *flags = 0;
 546                  return _GetGenericOptionsValue(options, optionName, type, value, index);
 547 krisbash 1.1 }
 548              
 549              MI_Result MI_CALL GenericOptions_GetOptionCount(
 550                  _In_   const struct _GenericOptions_Handle *options,
 551                  _Out_ MI_Uint32 *count)
 552              {
 553                  if ((options == NULL) || (count == NULL))
 554                      return MI_RESULT_INVALID_PARAMETER;
 555              
 556                  {
 557                      struct _GenericOptions *genericOptions = options->genericOptions;
 558                      if (genericOptions->optionsInstance)
 559                      {
 560                          return MI_Instance_GetElementCount(genericOptions->optionsInstance, count);
 561                      }
 562                      *count = 0;
 563                      return MI_RESULT_OK;
 564                  }
 565              }
 566              
 567              #ifdef _PREFAST_
 568 krisbash 1.1     #pragma prefast(push)
 569                  #pragma prefast(disable:28196) 
 570              #endif
 571              MI_Result MI_CALL GenericOptions_GetOptionAt(
 572                  _In_   const struct _GenericOptions_Handle *options,
 573                  MI_Uint32 index,
 574                  _Outptr_result_z_ const MI_Char **optionName,
 575                  _Out_ MI_Value *value,
 576                  _Out_ MI_Type *type,
 577                  _Out_opt_ MI_Uint32 *flags)
 578              {
 579                  if ((options == NULL) || (optionName == NULL) || (value == NULL) || (type == NULL))
 580                      return MI_RESULT_INVALID_PARAMETER;
 581              
 582                  {
 583                      struct _GenericOptions *genericOptions = options->genericOptions;
 584                      if (genericOptions->optionsInstance)
 585                      {
 586                          if (flags)
 587                              *flags = 0;
 588              
 589 krisbash 1.1             return  MI_Instance_GetElementAt(genericOptions->optionsInstance, index, optionName, value, type, 0);
 590                      }
 591                  }
 592                  return MI_RESULT_NO_SUCH_PROPERTY;
 593              }
 594              #ifdef _PREFAST_
 595                  #pragma prefast(pop)
 596              #endif
 597              
 598              MI_Result MI_CALL GenericOptions_AddCredentials(
 599                  _Inout_   struct _GenericOptions_Handle *options,
 600                  _In_z_ const MI_Char *optionName,
 601                  _In_   const MI_UserCredentials *credentials,
 602                          MI_Uint32 flags)
 603              {
 604                  struct _GenericOptions *genericOptions;
 605                  MI_Result miResult;
 606                  MI_Value credValue;
 607                  MI_Type credType;
 608                  MI_Uint32 credFlags;
 609                  MI_Instance *namedCredSetInstance;
 610 krisbash 1.1     MI_Instance *credValueInstance;
 611                  MI_Boolean needToAddCredInstance = MI_FALSE;
 612              
 613                  if ((options == NULL) || (options->genericOptions == NULL) || (options->genericOptions->batch == NULL) || (credentials == NULL) || (flags != 0))
 614                  {
 615                      return MI_RESULT_INVALID_PARAMETER;
 616                  }
 617                  
 618                  genericOptions = options->genericOptions;
 619              
 620                  /* ensure we have the credential set instance */
 621                  if (genericOptions->credentialInstance == NULL)
 622                  {
 623                      miResult = Instance_NewDynamic(&genericOptions->credentialInstance, MI_T("_MI_CredentialSet"), MI_FLAG_CLASS, genericOptions->batch);
 624                      if (miResult != MI_RESULT_OK)
 625                      {
 626                          return miResult;
 627                      }
 628                  }
 629              
 630                  /* ensure we have a named credential set for this credential  */
 631 krisbash 1.1     miResult = MI_Instance_GetElement(genericOptions->credentialInstance, optionName, &credValue, &credType, &credFlags, NULL);
 632                  if (miResult == MI_RESULT_NO_SUCH_PROPERTY)
 633                  {
 634                      miResult = Instance_NewDynamic(&credValue.instance, MI_T("_MI_NamedCredentialSet"), MI_FLAG_CLASS, genericOptions->batch);
 635                      if (miResult != MI_RESULT_OK)
 636                      {
 637                          return miResult;
 638                      }
 639                      miResult = MI_Instance_AddElement(genericOptions->credentialInstance, optionName, &credValue, MI_INSTANCE, MI_FLAG_BORROW);
 640                      if (miResult != MI_RESULT_OK)
 641                      {
 642                          return miResult;
 643                      }
 644                  }
 645                  else if (miResult != MI_RESULT_OK)
 646                      return miResult;
 647              
 648                  namedCredSetInstance = credValue.instance;
 649              
 650                  /* Ensure we have a credential option for this credential type */
 651                  miResult = MI_Instance_GetElement(namedCredSetInstance, credentials->authenticationType, &credValue, &credType, &credFlags, NULL);
 652 krisbash 1.1     if (miResult == MI_RESULT_NO_SUCH_PROPERTY)
 653                  {
 654                      miResult = Instance_NewDynamic(&credValueInstance, MI_T("_MI_CredentialValue"), MI_FLAG_CLASS, genericOptions->batch);
 655                      if (miResult != MI_RESULT_OK)
 656                      {
 657                          return miResult;
 658                      }
 659                      needToAddCredInstance = MI_TRUE;
 660                  }
 661                  else if (miResult != MI_RESULT_OK)
 662                      return miResult;
 663                  else
 664                  {
 665                      /* Cannot add the same element more than once, so fail */
 666                      return MI_RESULT_FAILED;
 667                  }
 668              
 669                  /* Now we can add the credentials to this credential value */
 670                  if ((Tcscmp(credentials->authenticationType, MI_AUTH_TYPE_NONE) == 0) ||
 671                      (Tcscmp(credentials->authenticationType, MI_AUTH_TYPE_NEGO_NO_CREDS) == 0) ||
 672                      (Tcscmp(credentials->authenticationType, MI_AUTH_TYPE_DEFAULT) == 0))
 673 krisbash 1.1     {
 674                      /* We are done as there are no more items to store */
 675                  }
 676                  else if ((Tcscmp(credentials->authenticationType, MI_AUTH_TYPE_DIGEST) == 0) ||
 677                           (Tcscmp(credentials->authenticationType, MI_AUTH_TYPE_NEGO_WITH_CREDS) == 0) ||
 678                           (Tcscmp(credentials->authenticationType, MI_AUTH_TYPE_BASIC) == 0) ||
 679                           (Tcscmp(credentials->authenticationType, MI_AUTH_TYPE_KERBEROS) == 0) ||
 680                           (Tcscmp(credentials->authenticationType, MI_AUTH_TYPE_NTLM) == 0)
 681              #if (WINVER >= 0x600)
 682                           || (Tcscmp(credentials->authenticationType, MI_AUTH_TYPE_CREDSSP) == 0)
 683              #endif
 684                           )
 685                  {
 686                      /* domain/username/password */
 687                      if (credentials->credentials.usernamePassword.domain == NULL)
 688                      {
 689                          if (needToAddCredInstance)
 690                              miResult = MI_Instance_AddElement(credValueInstance, MI_T("Domain"), NULL, MI_STRING, MI_FLAG_NULL);
 691                          else
 692                              miResult = MI_Instance_SetElement(credValueInstance, MI_T("Domain"), NULL, MI_STRING, MI_FLAG_NULL);
 693                      }
 694 krisbash 1.1         else
 695                      {
 696                          credValue.string = (MI_String) credentials->credentials.usernamePassword.domain;
 697                          if (needToAddCredInstance)
 698                              miResult = MI_Instance_AddElement(credValueInstance, MI_T("Domain"), &credValue, MI_STRING, 0);
 699                          else
 700                              miResult = MI_Instance_SetElement(credValueInstance, MI_T("Domain"), &credValue, MI_STRING, 0);
 701                      }
 702                      if (miResult != MI_RESULT_OK)
 703                          return miResult;
 704              
 705                      if (credentials->credentials.usernamePassword.username == NULL)
 706                      {
 707                          /* Illegal to not have a username */
 708                          miResult = MI_RESULT_INVALID_PARAMETER;
 709                      }
 710                      else
 711                      {
 712                          credValue.string = (MI_String) credentials->credentials.usernamePassword.username;
 713                          if (needToAddCredInstance)
 714                              miResult = MI_Instance_AddElement(credValueInstance, MI_T("Username"), &credValue, MI_STRING, 0);
 715 krisbash 1.1             else
 716                              miResult = MI_Instance_SetElement(credValueInstance, MI_T("Username"), &credValue, MI_STRING, 0);
 717                      }
 718                      if (miResult != MI_RESULT_OK)
 719                          return miResult;
 720              
 721              
 722                      if (credentials->credentials.usernamePassword.password == NULL)
 723                      {
 724                          if (needToAddCredInstance)
 725                              miResult = MI_Instance_AddElement(credValueInstance, MI_T("Password"), NULL, MI_STRING, MI_FLAG_NULL);
 726                          else
 727                              miResult = MI_Instance_SetElement(credValueInstance, MI_T("Password"), NULL, MI_STRING, MI_FLAG_NULL);
 728                      }
 729                      else
 730                      {
 731                          MI_Uint32 bufferNeeded;
 732                          MI_Uint32 sourceBufferLength = (Tcslen(credentials->credentials.usernamePassword.password)+1)*sizeof(MI_Char);
 733                          int encryptRet;
 734              
 735                          encryptRet = EncryptData(credentials->credentials.usernamePassword.password, sourceBufferLength, NULL, 0, &bufferNeeded);
 736 krisbash 1.1             if (encryptRet != -2)
 737                              return MI_RESULT_FAILED;
 738              
 739                          credValue.uint8a.size = bufferNeeded;
 740                          credValue.uint8a.data = Batch_Get(options->genericOptions->batch, bufferNeeded);
 741                          if (credValue.uint8a.data == NULL)
 742                              return MI_RESULT_SERVER_LIMITS_EXCEEDED;
 743              
 744                          encryptRet = EncryptData(credentials->credentials.usernamePassword.password, sourceBufferLength, credValue.uint8a.data, bufferNeeded, &bufferNeeded);
 745                          if (encryptRet != 0)
 746                              return MI_RESULT_FAILED;
 747              
 748                          if (needToAddCredInstance)
 749                              miResult = MI_Instance_AddElement(credValueInstance, MI_T("Password"), &credValue, MI_UINT8A, 0);
 750                          else
 751                              miResult = MI_Instance_SetElement(credValueInstance, MI_T("Password"), &credValue, MI_UINT8A, 0);
 752                      }
 753                      if (miResult != MI_RESULT_OK)
 754                          return miResult;
 755                  }
 756                  else if ((Tcscmp(credentials->authenticationType, MI_AUTH_TYPE_CLIENT_CERTS) == 0) ||
 757 krisbash 1.1              (Tcscmp(credentials->authenticationType, MI_AUTH_TYPE_ISSUER_CERT) == 0))
 758                  {
 759                      /* Certificate thumbprint */
 760                      if (credentials->credentials.certificateThumbprint == NULL)
 761                      {
 762                          if (needToAddCredInstance)
 763                              miResult = MI_Instance_AddElement(credValueInstance, MI_T("Thumbprint"), NULL, MI_STRING, MI_FLAG_NULL);
 764                          else
 765                              miResult = MI_Instance_SetElement(credValueInstance, MI_T("Thumbprint"), NULL, MI_STRING, MI_FLAG_NULL);
 766                      }
 767                      else
 768                      {
 769                          credValue.string = (MI_String) credentials->credentials.certificateThumbprint;
 770                          if (needToAddCredInstance)
 771                              miResult = MI_Instance_AddElement(credValueInstance, MI_T("Thumbprint"), &credValue, MI_STRING, 0);
 772                          else
 773                              miResult = MI_Instance_SetElement(credValueInstance, MI_T("Thumbprint"), &credValue, MI_STRING, 0);
 774                      }
 775                      if (miResult != MI_RESULT_OK)
 776                          return miResult;
 777                  }
 778 krisbash 1.1     else
 779                  {
 780                      return MI_RESULT_INVALID_PARAMETER;
 781                  }
 782              
 783                  if ((miResult == MI_RESULT_OK) && needToAddCredInstance)
 784                  {
 785                      credValue.instance = credValueInstance;
 786                      miResult = MI_Instance_AddElement(namedCredSetInstance, credentials->authenticationType, &credValue, MI_INSTANCE, MI_FLAG_BORROW);
 787                      if (miResult != MI_RESULT_OK)
 788                      {
 789                          return miResult;
 790                      }
 791                  }
 792                  return miResult;
 793              }
 794              
 795              MI_Result MI_CALL GenericOptions_GetCredentialsCount(
 796                  _In_   const struct _GenericOptions_Handle *options,
 797                  _Out_ MI_Uint32 *count)
 798              {
 799 krisbash 1.1     struct _GenericOptions *genericOptions;
 800                  MI_Result miResult;
 801                  MI_Value credValue;
 802                  MI_Type credType;
 803                  MI_Instance *namedCredSetInstance;
 804                  MI_Uint32 credInstElemCount = 0;
 805                  MI_Uint32 credInstElemIndex = 0;
 806                  MI_Uint32 namedCredValueCount = 0;
 807              
 808                  if ((options == NULL) || (options->genericOptions == NULL) || (options->genericOptions->batch == NULL) || (count == NULL))
 809                  {
 810                      return MI_RESULT_INVALID_PARAMETER;
 811                  }
 812                  
 813                  genericOptions = options->genericOptions;
 814              
 815                  *count = 0;
 816              
 817                  /* Do we have any creds at all? */
 818                  if (genericOptions->credentialInstance == NULL)
 819                  {
 820 krisbash 1.1         return MI_RESULT_OK;
 821                  }
 822              
 823                  miResult = MI_Instance_GetElementCount(genericOptions->credentialInstance, &credInstElemCount);
 824                  if (miResult != MI_RESULT_OK)
 825                  {
 826                      *count = 0;
 827                      return miResult;
 828                  }
 829              
 830                  for (credInstElemIndex = 0; credInstElemIndex != credInstElemCount; credInstElemIndex++)
 831                  {
 832                      /* Count the named credential list  */
 833                      miResult = MI_Instance_GetElementAt(genericOptions->credentialInstance, credInstElemIndex, NULL, &credValue, &credType, NULL);
 834                      if (miResult != MI_RESULT_OK)
 835                      {
 836                          *count = 0;
 837                          return miResult;
 838                      }
 839              
 840                      namedCredSetInstance = credValue.instance;
 841 krisbash 1.1 
 842                      /* Count the creds inside the named credential list */
 843                      miResult = MI_Instance_GetElementCount(namedCredSetInstance, &namedCredValueCount);
 844                      if (miResult != MI_RESULT_OK)
 845                      {
 846                          *count = 0;
 847                          return miResult;
 848                      }
 849              
 850                      *count += namedCredValueCount;
 851                  }
 852                  return MI_RESULT_OK;
 853              }
 854              
 855              _Success_(return == MI_RESULT_OK)
 856              MI_Result _GetCredentialInstanceAt(_In_   struct _GenericOptions *genericOptions,
 857                  MI_Uint32 index,
 858                  _Outptr_result_z_ const MI_Char **optionName,
 859                  _Outptr_result_z_ const MI_Char **authenticationType,
 860                  _Outptr_ MI_Instance **credsInstance)
 861              {
 862 krisbash 1.1     MI_Result miResult;
 863                  MI_Value credValue;
 864                  MI_Type credType;
 865                  MI_Instance *namedCredSetInstance;
 866                  MI_Uint32 credInstElemCount = 0;
 867                  MI_Uint32 credInstElemIndex = 0;
 868                  MI_Uint32 namedCredValueCount = 0;
 869                  MI_Uint32 currentCount = 0;
 870              
 871                  miResult = MI_Instance_GetElementCount(genericOptions->credentialInstance, &credInstElemCount);
 872                  if (miResult != MI_RESULT_OK)
 873                  {
 874                      return miResult;
 875                  }
 876              
 877                  for (credInstElemIndex = 0; credInstElemIndex != credInstElemCount; credInstElemIndex++)
 878                  {
 879                      const MI_Char *tempCredName;
 880                      /* Count the named credential list  */
 881                      miResult = MI_Instance_GetElementAt(genericOptions->credentialInstance, credInstElemIndex, &tempCredName, &credValue, &credType, NULL);
 882              
 883 krisbash 1.1         if (miResult != MI_RESULT_OK)
 884                      {
 885                          return miResult;
 886                      }
 887                      if (credType != MI_INSTANCE)
 888                          return MI_RESULT_INVALID_PARAMETER;
 889              
 890              #ifdef _PREFAST_
 891                      _Analysis_assume_(tempCredName != NULL);
 892              #endif
 893              
 894                      namedCredSetInstance = credValue.instance;
 895              
 896                      /* Count the creds inside the named credential list */
 897                      miResult = MI_Instance_GetElementCount(namedCredSetInstance, &namedCredValueCount);
 898                      if (miResult != MI_RESULT_OK)
 899                      {
 900                          return miResult;
 901                      }
 902              
 903                      if ((currentCount + namedCredValueCount) > index)
 904 krisbash 1.1         {
 905                          MI_Value credDetailsValue;
 906                          MI_Type credDetailsValueType;
 907                          const MI_Char *credDetailAuthName;
 908                          /* The value is in this batch of items */
 909                          miResult = MI_Instance_GetElementAt(namedCredSetInstance, index - currentCount, &credDetailAuthName, &credDetailsValue, &credDetailsValueType, NULL);
 910              
 911                          if (miResult != MI_RESULT_OK)
 912                              return miResult;
 913                          if (credDetailsValueType != MI_INSTANCE)
 914                              return MI_RESULT_INVALID_PARAMETER;
 915              
 916              #ifdef _PREFAST_
 917                          _Analysis_assume_(credDetailAuthName != NULL);
 918              #endif
 919              
 920                          /* Got the item we need, now set up out parameters */
 921                          *authenticationType = credDetailAuthName;
 922                          *optionName = tempCredName;
 923                          *credsInstance = credDetailsValue.instance;
 924                          return MI_RESULT_OK;
 925 krisbash 1.1         }
 926                      else
 927                      {
 928                          /* Not in this batch so continue on, counting how many we found this time around */
 929                          currentCount += namedCredValueCount;
 930                      }
 931                  }
 932                  return MI_RESULT_NO_SUCH_PROPERTY;
 933              }
 934              
 935              _Success_(return == MI_RESULT_OK)
 936              MI_Result MI_CALL GenericOptions_GetCredentialsAt(
 937                  _In_   const struct _GenericOptions_Handle *options,
 938                  MI_Uint32 index,
 939                  _Outptr_result_z_ const MI_Char **optionName,
 940                  _Out_ MI_UserCredentials *credentials, // output credentials always has password set to '******'
 941                  _Out_opt_ MI_Uint32 *flags)
 942              {
 943                  struct _GenericOptions *genericOptions;
 944                  MI_Instance *credInstance;
 945                  MI_Result miResult;
 946 krisbash 1.1     const MI_Char *authenticationType;
 947              
 948                  if ((options == NULL) || (options->genericOptions == NULL) || (options->genericOptions->batch == NULL) || (options->genericOptions->credentialInstance == NULL) || (credentials == NULL) || (optionName == NULL))
 949                  {
 950                      return MI_RESULT_INVALID_PARAMETER;
 951                  }
 952                  
 953                  genericOptions = options->genericOptions;
 954              
 955                  if (flags)
 956                      *flags = 0;
 957              
 958                  miResult = _GetCredentialInstanceAt(genericOptions, index, optionName, &authenticationType, &credInstance);
 959                  if (miResult != MI_RESULT_OK)
 960                      return miResult;
 961              
 962                  memset(credentials, 0,  sizeof(*credentials));
 963              
 964                  /* Decode instance for cred structure */
 965                  /* Now we can add the credentials to this credential value */
 966                  if ((Tcscmp(authenticationType, MI_AUTH_TYPE_NONE) == 0) ||
 967 krisbash 1.1         (Tcscmp(authenticationType, MI_AUTH_TYPE_NEGO_NO_CREDS) == 0) ||
 968                      (Tcscmp(authenticationType, MI_AUTH_TYPE_DEFAULT) == 0))
 969                  {
 970                      /* We are done as there are no more items to store */
 971                  }
 972                  else if ((Tcscmp(authenticationType, MI_AUTH_TYPE_DIGEST) == 0) ||
 973                           (Tcscmp(authenticationType, MI_AUTH_TYPE_NEGO_WITH_CREDS) == 0) ||
 974                           (Tcscmp(authenticationType, MI_AUTH_TYPE_BASIC) == 0) ||
 975                           (Tcscmp(authenticationType, MI_AUTH_TYPE_KERBEROS) == 0) ||
 976                           (Tcscmp(authenticationType, MI_AUTH_TYPE_NTLM) == 0)
 977              #if (WINVER >= 0x600)
 978                           || (Tcscmp(authenticationType, MI_AUTH_TYPE_CREDSSP) == 0)
 979              #endif
 980                           )
 981                  {
 982                      /* domain/username/password */
 983                      MI_Value tmpValue;
 984                      MI_Type tmpType;
 985                      MI_Uint32 tmpFlags;
 986              
 987                      miResult = MI_Instance_GetElement(credInstance, MI_T("Domain"), &tmpValue, &tmpType, &tmpFlags, NULL);
 988 krisbash 1.1         if (miResult != MI_RESULT_OK)
 989                      {
 990                          return miResult;
 991                      }
 992                      else if (tmpType != MI_STRING)
 993                      {
 994                          return MI_RESULT_INVALID_PARAMETER;
 995                      }
 996                      if (tmpFlags & MI_FLAG_NULL)
 997                      {
 998                          credentials->credentials.usernamePassword.domain = NULL;
 999                      }
1000                      else
1001                      {
1002                          credentials->credentials.usernamePassword.domain = tmpValue.string;
1003                      }
1004              
1005                      miResult = MI_Instance_GetElement(credInstance, MI_T("Username"), &tmpValue, &tmpType, &tmpFlags, NULL);
1006                      if (miResult != MI_RESULT_OK)
1007                      {
1008                          return miResult;
1009 krisbash 1.1         }
1010                      else if (tmpType != MI_STRING)
1011                      {
1012                          return MI_RESULT_INVALID_PARAMETER;
1013                      }
1014                      if (tmpFlags & MI_FLAG_NULL)
1015                      {
1016                          credentials->credentials.usernamePassword.username = NULL;
1017                      }
1018                      else
1019                      {
1020                          credentials->credentials.usernamePassword.username = tmpValue.string;
1021                      }
1022              
1023                      credentials->credentials.usernamePassword.password = MI_T("******");
1024                  }
1025                  else if ((Tcscmp(authenticationType, MI_AUTH_TYPE_CLIENT_CERTS) == 0) ||
1026                           (Tcscmp(authenticationType, MI_AUTH_TYPE_ISSUER_CERT) == 0))
1027                  {
1028                      /* Certificate thumbprint */
1029                      MI_Value tmpValue;
1030 krisbash 1.1         MI_Type tmpType;
1031                      MI_Uint32 tmpFlags;
1032                      miResult = MI_Instance_GetElement(credInstance, MI_T("Thumbprint"), &tmpValue, &tmpType, &tmpFlags, NULL);
1033                      if ((miResult != MI_RESULT_OK) || (tmpType != MI_STRING))
1034                      {
1035                          return miResult;
1036                      }
1037                      if (tmpFlags & MI_FLAG_NULL)
1038                      {
1039                          credentials->credentials.certificateThumbprint = NULL;
1040                      }
1041                      else
1042                      {
1043                          credentials->credentials.certificateThumbprint = tmpValue.string;
1044                      }
1045                  }
1046                  else
1047                  {
1048                      return MI_RESULT_INVALID_PARAMETER;
1049                  }
1050              
1051 krisbash 1.1     credentials->authenticationType = authenticationType;
1052              
1053                  return MI_RESULT_OK;
1054              }
1055              
1056              _Success_(return == MI_RESULT_OK)
1057              MI_Result MI_CALL GenericOptions_GetCredentialsPasswordAt (
1058                  _In_   const struct _GenericOptions_Handle *options,
1059                  MI_Uint32 index,
1060                  _Outptr_result_z_ const MI_Char **optionName,
1061                  _Out_writes_to_opt_(bufferLength, *passwordLength) MI_Char *password,
1062                  _In_ MI_Uint32 bufferLength,
1063                  _When_(bufferLength == 0, _Out_) MI_Uint32 *passwordLength,
1064                  _Out_opt_ MI_Uint32 *flags)
1065              {
1066                  struct _GenericOptions *genericOptions;
1067                  MI_Instance *credInstance;
1068                  MI_Result miResult;
1069                  const MI_Char *authenticationType;
1070              
1071                  if ((options == NULL) || (options->genericOptions == NULL) || (options->genericOptions->batch == NULL) || (options->genericOptions->credentialInstance == NULL) || (optionName == NULL) || (passwordLength == NULL))
1072 krisbash 1.1     {
1073                      return MI_RESULT_INVALID_PARAMETER;
1074                  }
1075                  
1076                  genericOptions = options->genericOptions;
1077              
1078                  if (flags)
1079                      *flags = 0;
1080              
1081                  miResult = _GetCredentialInstanceAt(genericOptions, index, optionName, &authenticationType, &credInstance);
1082                  if (miResult != MI_RESULT_OK)
1083                      return miResult;
1084              
1085                  /* Decode instance for password */
1086                  if ((Tcscmp(authenticationType, MI_AUTH_TYPE_DIGEST) == 0) ||
1087                           (Tcscmp(authenticationType, MI_AUTH_TYPE_NEGO_WITH_CREDS) == 0) ||
1088                           (Tcscmp(authenticationType, MI_AUTH_TYPE_BASIC) == 0) ||
1089                           (Tcscmp(authenticationType, MI_AUTH_TYPE_KERBEROS) == 0) ||
1090                           (Tcscmp(authenticationType, MI_AUTH_TYPE_NTLM) == 0)
1091              #if (WINVER >= 0x600)
1092                           || (Tcscmp(authenticationType, MI_AUTH_TYPE_CREDSSP) == 0)
1093 krisbash 1.1 #endif
1094                           )
1095                  {
1096                      /* domain/username/password */
1097                      MI_Value tmpValue;
1098                      MI_Type tmpType;
1099                      MI_Uint32 tmpFlags;
1100              
1101                      miResult = MI_Instance_GetElement(credInstance, MI_T("Password"), &tmpValue, &tmpType, &tmpFlags, NULL);
1102                      if (miResult != MI_RESULT_OK)
1103                      {
1104                          return miResult;
1105                      }
1106                      else if (tmpType != MI_UINT8A)
1107                      {
1108                          return MI_RESULT_INVALID_PARAMETER;
1109                      }
1110                      if (tmpFlags & MI_FLAG_NULL)
1111                      {
1112                          *passwordLength = 0;
1113                          return MI_RESULT_OK;
1114 krisbash 1.1         }
1115                      else
1116                      {
1117                          MI_Uint32 neededLength;
1118                          MI_Uint32 allocatedLength;
1119                          MI_Char *tmpPassword = NULL;
1120                          int decryptRet = DecryptData(tmpValue.array.data, tmpValue.array.size, NULL, 0, &neededLength);
1121                          if (decryptRet != -2)
1122                              return MI_RESULT_FAILED;
1123                          allocatedLength = neededLength;
1124                          tmpPassword = PAL_Malloc(allocatedLength);
1125                          if (tmpPassword == NULL)
1126                              return MI_RESULT_SERVER_LIMITS_EXCEEDED;
1127              
1128                          decryptRet = DecryptData(tmpValue.array.data, tmpValue.array.size, tmpPassword, neededLength, &neededLength);
1129                          if (decryptRet != 0)
1130                          {
1131              #if defined(_MSC_VER)
1132                              SecureZeroMemory(tmpPassword, allocatedLength);
1133              #endif
1134                              PAL_Free(tmpPassword);
1135 krisbash 1.1                 return MI_RESULT_FAILED;
1136                          }
1137                          _Analysis_assume_nullterminated_(tmpPassword);
1138                          *passwordLength = Tcslen(tmpPassword)+1;
1139                          if (bufferLength < *passwordLength)
1140                          {
1141              #if defined(_MSC_VER)
1142                              SecureZeroMemory(tmpPassword, allocatedLength);
1143              #endif
1144                              PAL_Free(tmpPassword);
1145                              if (bufferLength == 0)
1146                                  return MI_RESULT_OK;
1147                              else
1148                                  return MI_RESULT_FAILED;
1149                          }
1150                          Tcslcpy(password, tmpPassword, bufferLength);
1151              #if defined(_MSC_VER)
1152                          SecureZeroMemory(tmpPassword, allocatedLength);
1153              #endif
1154                          PAL_Free(tmpPassword);
1155                          return MI_RESULT_OK;
1156 krisbash 1.1         }
1157                  }
1158                  else
1159                      return MI_RESULT_INVALID_PARAMETER;
1160              }
1161              
1162              
1163              MI_Result MI_CALL GenericOptions_GetEnabledChannels(
1164                      _In_   const MI_OperationOptions *options_,
1165                      _In_z_ const MI_Char *optionName,
1166                      _Out_writes_to_opt_(bufferLength, *channelCount) MI_Uint32 *channels,
1167                      _In_ MI_Uint32 bufferLength,
1168                      _Out_ MI_Uint32 *channelCount,
1169                      _Out_opt_ MI_Uint32 *flags)
1170              {
1171                  struct _GenericOptions_Handle * options = (struct _GenericOptions_Handle *) options_;
1172                  MI_Result miResult;
1173                  MI_Type tmpType;
1174                  MI_Value tmpValue;
1175                  
1176                  if ((options == NULL) || (options->genericOptions == NULL) || (optionName == NULL) || (channelCount == NULL))
1177 krisbash 1.1         return MI_RESULT_INVALID_PARAMETER;
1178                  
1179                  if (flags)
1180                      *flags = 0;
1181                      
1182                  if (options->genericOptions->optionsInstance == NULL)
1183                  {
1184                      *channelCount = 0;
1185                      return MI_RESULT_OK;
1186                  }
1187                  miResult = _GetGenericOptionsValue(options, optionName, &tmpType, &tmpValue, NULL);
1188                  if (miResult == MI_RESULT_NO_SUCH_PROPERTY)
1189                  {
1190                      *channelCount = 0;
1191                      return MI_RESULT_OK;
1192                  }
1193              
1194                  if ((Tcscmp(optionName, MI_T("__MI_OPERATIONOPTIONS_CHANNEL")) != 0) || 
1195                      (tmpType != MI_UINT32A))
1196                  {
1197                      return MI_RESULT_TYPE_MISMATCH;
1198 krisbash 1.1     }
1199              
1200                  *channelCount = tmpValue.uint32a.size;
1201              
1202                  if (bufferLength >= tmpValue.uint32a.size)
1203                  {
1204                      if (channels == NULL)
1205                          return MI_RESULT_INVALID_PARAMETER;
1206              
1207                      memcpy(channels, tmpValue.uint32a.data, sizeof(MI_Uint32)*tmpValue.uint32a.size);
1208                      return MI_RESULT_OK;
1209                  }
1210                  return MI_RESULT_FAILED;;
1211              }
1212              
1213              #if defined(_MSC_VER)
1214              _Success_(return == MI_RESULT_OK)
1215              MI_Result GetCurrentThreadPreferredUILanguage(_Out_writes_z_(size) MI_Char* Locale, size_t size)
1216              {
1217                  MI_Char stackBuffer[MI_MAX_LOCALE_SIZE];
1218                  ULONG numLangs = 0;
1219 krisbash 1.1     ULONG lenBuffer = 0;
1220                  PZZWSTR buffer;
1221                  MI_Result r = MI_RESULT_OK;
1222                  size_t lenLocale;
1223              
1224                  if (size)
1225                  {
1226                      Locale[0] = L'\0';
1227                  }
1228                  else
1229                      return MI_RESULT_FAILED;
1230              
1231                  if (!GetThreadPreferredUILanguages(0, &numLangs, NULL, &lenBuffer))
1232                  {
1233                      /* return ResultFromHRESULT(HRESULT_FROM_WIN32(GetLastError())); */
1234                      return MI_RESULT_FAILED;
1235                  }
1236              
1237                  if (lenBuffer <= MI_MAX_LOCALE_SIZE)
1238                  {
1239                      buffer = stackBuffer;
1240 krisbash 1.1     }
1241                  else
1242                  {
1243                      buffer = PAL_Malloc(sizeof(MI_Char) * lenBuffer);
1244                  }
1245                  if (buffer == NULL)
1246                  {
1247                      return MI_RESULT_SERVER_LIMITS_EXCEEDED;
1248                  }
1249              
1250                  if (!GetThreadPreferredUILanguages(0, &numLangs, buffer, &lenBuffer))
1251                  {
1252                      /* r = ResultFromHRESULT(HRESULT_FROM_WIN32(GetLastError())); */
1253                      r = MI_RESULT_FAILED;
1254                      goto CleanUp;
1255                  }
1256              
1257                  // Read the first locale
1258                  lenLocale = Tcslen(buffer) + 1;
1259                  if (size < lenLocale)
1260                  {
1261 krisbash 1.1         r = MI_RESULT_INVALID_PARAMETER;
1262                      goto CleanUp;
1263                  }
1264              
1265                  if (Tcslcpy(Locale, buffer, lenLocale) > lenLocale)
1266                  {
1267                      r = MI_RESULT_FAILED;
1268                  }
1269              
1270              CleanUp:
1271                  if (buffer != stackBuffer)
1272                  {
1273                      PAL_Free(buffer);
1274                  }
1275                  return r;
1276              }
1277              #endif
1278              
1279              MI_Result MI_CALL  DestinationOptions_Create(
1280                  _In_  MI_Application *application,
1281                  _Out_ MI_DestinationOptions *options)
1282 krisbash 1.1 {
1283                  MI_Result miResult;
1284                  
1285                  if ((application == NULL) || (options == NULL))
1286                      return MI_RESULT_INVALID_PARAMETER;
1287              
1288                  miResult = GenericOptions_Create((struct _GenericOptions_Handle *) options, &g_destinationOptionsFT);
1289                  if (miResult != MI_RESULT_OK)
1290                      return miResult;
1291              
1292              #if defined(_MSC_VER)
1293                  {
1294                      MI_Char currentLocale[MI_MAX_LOCALE_SIZE];
1295                      miResult = GetCurrentThreadPreferredUILanguage(currentLocale, sizeof(currentLocale)/sizeof(MI_Char));
1296                      if (miResult == MI_RESULT_OK)
1297                      {
1298                          if (((miResult = MI_DestinationOptions_SetDataLocale(options, currentLocale)) == MI_RESULT_OK) &&
1299                              ((miResult = MI_DestinationOptions_SetUILocale(options, currentLocale)) == MI_RESULT_OK))
1300                          {
1301                          }
1302                      }
1303 krisbash 1.1         if (miResult != MI_RESULT_OK)
1304                      {
1305                          MI_DestinationOptions_Delete(options);
1306                          options->reserved2 = (ptrdiff_t)NULL;
1307                          options->ft = 0;
1308                      }
1309                      return miResult;
1310                  }
1311              #else
1312                  return MI_RESULT_OK;
1313              #endif
1314              
1315              }
1316              MI_Result MI_CALL DestinationOptions_MigrateOptions(
1317                  _In_ const MI_DestinationOptions *source, 
1318                  _Inout_ MI_DestinationOptions *destination,
1319                  _In_opt_z_ const MI_Char *protocol,
1320                  _Outptr_opt_result_maybenull_ MI_Instance **extendedError)
1321              {
1322                  struct _GenericOptions_Handle *options_Handle = (struct _GenericOptions_Handle *)source;
1323                  MI_Uint32 optionCount, optionIndex;
1324 krisbash 1.1     MI_Result miResult;
1325              
1326                  if ((source == NULL) || (source->ft == NULL))
1327                      return MI_RESULT_OK;
1328              
1329                  if (extendedError != NULL)
1330                      *extendedError = NULL;
1331              
1332                  miResult = GenericOptions_GetOptionCount(options_Handle, &optionCount);
1333                  if (miResult != MI_RESULT_OK)
1334                      return miResult;
1335              
1336                  for (optionIndex = 0; optionIndex != optionCount; optionIndex++)
1337                  {
1338                      MI_Type optionType;
1339                      const MI_Char *optionName;
1340                      MI_Value optionValue;
1341              
1342                      miResult = MI_Instance_GetElementAt(options_Handle->genericOptions->optionsInstance, optionIndex, &optionName, &optionValue, &optionType, NULL);
1343                      if (miResult != MI_RESULT_OK)
1344                          return miResult;
1345 krisbash 1.1 
1346                      switch(optionType)
1347                      {
1348                      case MI_UINT32:
1349                      {
1350                          miResult = destination->ft->SetNumber(destination, optionName, optionValue.uint32, 0);
1351                          break;
1352                      }
1353                      case MI_STRING:
1354                      {
1355                          miResult = destination->ft->SetString(destination, optionName, optionValue.string, 0);
1356                          break;
1357                      }
1358                      case MI_DATETIME:
1359                      {
1360                          miResult = destination->ft->SetInterval(destination, optionName, &optionValue.datetime.u.interval, 0);
1361                          break;
1362                      }
1363                      default:
1364                          return MI_RESULT_INVALID_PARAMETER;
1365                      }
1366 krisbash 1.1 
1367                      if (miResult != MI_RESULT_OK)
1368                          return miResult;
1369                  }
1370              
1371                  /* Migrate credentials */
1372                  miResult = GenericOptions_GetCredentialsCount(options_Handle, &optionCount);
1373                  if (miResult != MI_RESULT_OK)
1374                      return miResult;
1375              
1376                  for (optionIndex = 0; optionIndex != optionCount; optionIndex++)
1377                  {
1378                      const MI_Char *optionName;
1379                      MI_Instance *credInstance;
1380                      MI_UserCredentials credentials;
1381                      MI_Uint32 passwordBufferSize = 0;
1382                      MI_Char *password = NULL;
1383              
1384                      memset(&credentials, 0, sizeof(credentials));
1385              
1386                      miResult = _GetCredentialInstanceAt(options_Handle->genericOptions, optionIndex, &optionName, &credentials.authenticationType, &credInstance);
1387 krisbash 1.1         if (miResult != MI_RESULT_OK)
1388                          return miResult;
1389              
1390                      if ((Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_DIGEST) == 0) ||
1391                               (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_NEGO_WITH_CREDS) == 0) ||
1392                               (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_BASIC) == 0) ||
1393                               (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_KERBEROS) == 0) ||
1394                               (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_NTLM) == 0)
1395              #if (WINVER >= 0x600)
1396                               || (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_CREDSSP) == 0)
1397              #endif
1398                               )
1399                      {
1400                              /* domain/Username/password */
1401                          /* domain/username/password */
1402                          MI_Value tmpValue;
1403                          MI_Type tmpType;
1404                          MI_Uint32 tmpFlags;
1405              
1406                          miResult = MI_Instance_GetElement(credInstance, MI_T("Domain"), &tmpValue, &tmpType, &tmpFlags, NULL);
1407                          if (miResult != MI_RESULT_OK)
1408 krisbash 1.1             {
1409                              return miResult;
1410                          }
1411                          else if (tmpType != MI_STRING)
1412                          {
1413                              return MI_RESULT_INVALID_PARAMETER;
1414                          }
1415                          if (tmpFlags & MI_FLAG_NULL)
1416                          {
1417                              credentials.credentials.usernamePassword.domain = NULL;
1418                          }
1419                          else
1420                          {
1421                              credentials.credentials.usernamePassword.domain = tmpValue.string;
1422                          }
1423              
1424                          miResult = MI_Instance_GetElement(credInstance, MI_T("Username"), &tmpValue, &tmpType, &tmpFlags, NULL);
1425                          if (miResult != MI_RESULT_OK)
1426                          {
1427                              return miResult;
1428                          }
1429 krisbash 1.1             else if (tmpType != MI_STRING)
1430                          {
1431                              return MI_RESULT_INVALID_PARAMETER;
1432                          }
1433                          if (tmpFlags & MI_FLAG_NULL)
1434                          {
1435                              credentials.credentials.usernamePassword.username = NULL;
1436                          }
1437                          else
1438                          {
1439                              credentials.credentials.usernamePassword.username = tmpValue.string;
1440                          }
1441              
1442                          miResult = MI_Instance_GetElement(credInstance, MI_T("Password"), &tmpValue, &tmpType, &tmpFlags, NULL);
1443                          if (miResult != MI_RESULT_OK)
1444                          {
1445                              return miResult;
1446                          }
1447                          else if (tmpType != MI_UINT8A)
1448                          {
1449                              return MI_RESULT_INVALID_PARAMETER;
1450 krisbash 1.1             }
1451                          if (tmpFlags & MI_FLAG_NULL)
1452                          {
1453                              credentials.credentials.usernamePassword.password = NULL;
1454                          }
1455                          else
1456                          {
1457                              MI_Uint32 bufferNeeded;
1458              
1459                              int decryptRet = DecryptData(tmpValue.uint8a.data, tmpValue.uint8a.size, NULL, 0, &bufferNeeded);
1460                              if (decryptRet != -2)
1461                                  return MI_RESULT_FAILED;
1462              
1463                              password = PAL_Malloc(bufferNeeded);
1464                              if (password == NULL)
1465                                  return MI_RESULT_SERVER_LIMITS_EXCEEDED;
1466              
1467                              passwordBufferSize = bufferNeeded;
1468              
1469                              decryptRet = DecryptData(tmpValue.uint8a.data, tmpValue.uint8a.size, password, passwordBufferSize, &bufferNeeded);
1470                              if (decryptRet != 0)
1471 krisbash 1.1                     return MI_RESULT_FAILED;
1472              
1473                              credentials.credentials.usernamePassword.password = password;
1474                          }
1475                          
1476                      }
1477                      else if ((Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_CLIENT_CERTS) == 0) ||
1478                               (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_ISSUER_CERT) == 0))
1479                      {
1480                          /* Thumbprint */
1481                          MI_Value tmpValue;
1482                          MI_Type tmpType;
1483                          MI_Uint32 tmpFlags;
1484                          miResult = MI_Instance_GetElement(credInstance, MI_T("Thumbprint"), &tmpValue, &tmpType, &tmpFlags, NULL);
1485                          if (miResult != MI_RESULT_OK)
1486                              return miResult;
1487                          if (tmpType != MI_STRING)
1488                              return MI_RESULT_INVALID_PARAMETER;
1489                          credentials.credentials.certificateThumbprint = tmpValue.string;
1490                      }
1491              
1492 krisbash 1.1         miResult = destination->ft->AddCredentials(destination, optionName, &credentials, 0);
1493                      if (password != NULL)
1494                      {
1495              #if defined(_MSC_VER)
1496                          SecureZeroMemory(password, passwordBufferSize);
1497              #endif
1498                          PAL_Free(password);
1499                      }
1500                      if (miResult != MI_RESULT_OK)
1501                          return miResult;
1502              
1503                  }
1504                  return MI_RESULT_OK;
1505              }
1506              
1507              void DestinationOptions_Duplicate(
1508                  _Inout_ const MI_DestinationOptions *source, 
1509                  _Out_ MI_DestinationOptions *destination)
1510              {
1511                  struct _GenericOptions_Handle *options = (struct _GenericOptions_Handle *)source;
1512                  memcpy(destination, source, sizeof(MI_DestinationOptions)) ;
1513 krisbash 1.1     if (options && options->genericOptions)
1514                  {
1515                      Atomic_Inc(&options->genericOptions->referenceCount);
1516                  }
1517              }
1518              
1519              MI_Result MI_CALL OperationOptions_Create(
1520                  _In_  MI_Application *application,
1521                  MI_Boolean customOptionsMustUnderstand,
1522                  _Out_ MI_OperationOptions *options_)
1523              {
1524                  MI_Result miResult;
1525                  struct _GenericOptions_Handle * options = (struct _GenericOptions_Handle *)options_;
1526                  
1527                  if ((application == NULL) || (options == NULL))
1528                      return MI_RESULT_INVALID_PARAMETER;
1529              
1530                  miResult = GenericOptions_Create(options, &g_operationOptionsFT);
1531              
1532                  if (miResult == MI_RESULT_OK)
1533                  {
1534 krisbash 1.1         /* Create the default channel configuration */
1535                      if (((miResult = GenericOptions_SetNumber(options, MI_T("__MI_OPERATIONOPTIONS_CHANNEL"), MI_WRITEMESSAGE_CHANNEL_WARNING, 0)) == MI_RESULT_OK) &&
1536                          ((miResult = GenericOptions_SetNumber(options, MI_T("__MI_OPERATIONOPTIONS_CHANNEL"), MI_WRITEMESSAGE_CHANNEL_VERBOSE, 0)) == MI_RESULT_OK) &&
1537                          ((miResult = GenericOptions_SetNumber(options, MI_T("__MI_OPERATIONOPTIONS_CHANNEL"), MI_WRITEMESSAGE_CHANNEL_DEBUG, 0)) == MI_RESULT_OK))
1538                      {
1539                      }
1540                  }
1541              
1542                  return miResult;
1543              }
1544              
1545              MI_Result MI_CALL OperationOptions_MigrateOptions(
1546                  _In_opt_ const MI_OperationOptions *source, 
1547                  _Inout_ MI_OperationOptions *destination)
1548              {
1549                  struct _GenericOptions_Handle *options_Handle = (struct _GenericOptions_Handle *)source;
1550                  MI_Uint32 optionCount, optionIndex;
1551                  MI_Result miResult;
1552              
1553                  if ((source == NULL) || (source->ft == NULL))
1554                      return MI_RESULT_OK;
1555 krisbash 1.1 
1556                  miResult = GenericOptions_GetOptionCount(options_Handle, &optionCount);
1557                  if (miResult != MI_RESULT_OK)
1558                      return miResult;
1559              
1560                  for (optionIndex = 0; optionIndex != optionCount; optionIndex++)
1561                  {
1562                      MI_Type optionType;
1563                      const MI_Char *optionName;
1564                      MI_Value optionValue;
1565              
1566                      miResult = MI_Instance_GetElementAt(options_Handle->genericOptions->optionsInstance, optionIndex, &optionName, &optionValue, &optionType, NULL);
1567                      if (miResult != MI_RESULT_OK)
1568                          return miResult;
1569                      switch(optionType)
1570                      {
1571                      case MI_UINT32:
1572                      {
1573                          miResult = destination->ft->SetNumber(destination, optionName, optionValue.uint32, 0);
1574                          break;
1575                      }
1576 krisbash 1.1         case MI_STRING:
1577                      {
1578                          miResult = destination->ft->SetString(destination, optionName, optionValue.string, 0);
1579                          break;
1580                      }
1581                      case MI_DATETIME:
1582                      {
1583                          if (optionValue.datetime.isTimestamp == MI_TRUE)
1584                              return MI_RESULT_INVALID_PARAMETER;
1585              
1586                          miResult = destination->ft->SetInterval(destination, optionName, &optionValue.datetime.u.interval, 0);
1587                          break;
1588                      }
1589                      case MI_UINT32A:
1590                      {
1591                          /* This is potentially the channel settings */
1592                          if (Tcscmp(optionName, MI_T("__MI_OPERATIONOPTIONS_CHANNEL")) == 0)
1593                          {
1594                              MI_Uint32 index;
1595                              for (index = 0; index != optionValue.uint32a.size; index++)
1596                              {
1597 krisbash 1.1                     miResult = destination->ft->SetNumber(destination, optionName, optionValue.uint32a.data[index], 0);
1598                                  if (miResult != MI_RESULT_OK)
1599                                      return miResult;
1600                              }
1601                          }
1602                          else
1603                          {
1604                              return MI_RESULT_INVALID_PARAMETER;
1605                          }
1606                          break;
1607                      }
1608                      case MI_INSTANCE:
1609                      {
1610                          if (Tcscmp(optionValue.instance->classDecl->name, MI_T("_OMI_CustomOptionValue")) == 0)
1611                          {
1612                              MI_Type mustUnderstandType;
1613                              MI_Value mustUnderstandValue;
1614                              MI_Type customOptionType;
1615                              MI_Value customOptionValue;
1616              
1617                              miResult = MI_Instance_GetElement(optionValue.instance, MI_T("value"), &customOptionValue, &customOptionType, NULL, NULL);
1618 krisbash 1.1                 if (miResult != MI_RESULT_OK)
1619                                  return miResult;
1620                              
1621                              miResult = MI_Instance_GetElement(optionValue.instance, MI_T("mustUnderstand"), &mustUnderstandValue, &mustUnderstandType, NULL, NULL);
1622                              if (miResult != MI_RESULT_OK)
1623                                  return miResult;
1624                              if (mustUnderstandType != MI_BOOLEAN)
1625                                  return MI_RESULT_INVALID_PARAMETER;
1626              
1627                              miResult = destination->ft->SetCustomOption(destination, optionName, customOptionType, &customOptionValue, mustUnderstandValue.boolean, 0);
1628              
1629                          }
1630                          else
1631                              return MI_RESULT_INVALID_PARAMETER;
1632                          break;
1633                      }
1634                      default:
1635                          return MI_RESULT_INVALID_PARAMETER;
1636                      }
1637              
1638                      if (miResult != MI_RESULT_OK)
1639 krisbash 1.1             return miResult;
1640                  }
1641              
1642                  return MI_RESULT_OK;
1643              }
1644              
1645              MI_Result MI_CALL  SubscriptionDeliveryOptions_Create(
1646                  _In_  MI_Application *application,
1647                  _In_  MI_SubscriptionDeliveryType deliveryType,
1648                  _Out_ MI_SubscriptionDeliveryOptions *options)
1649              {
1650                  if ((application == NULL) || (options == NULL))
1651                      return MI_RESULT_INVALID_PARAMETER;
1652              
1653                  return GenericOptions_Create((struct _GenericOptions_Handle *) options, &g_subscriptionDeliveryOptionsFT);
1654              }
1655              
1656              MI_Result MI_CALL SubscriptionDeliveryOptions_MigrateOptions(
1657                  _In_ const MI_SubscriptionDeliveryOptions *source, 
1658                  _Inout_ MI_SubscriptionDeliveryOptions *destination)
1659              {
1660 krisbash 1.1      struct _GenericOptions_Handle *options_Handle = (struct _GenericOptions_Handle *)source;
1661                  MI_Uint32 optionCount, optionIndex;
1662                  MI_Result miResult;
1663              
1664                  if ((source == NULL) || (source->ft == NULL))
1665                      return MI_RESULT_OK;
1666              
1667                  miResult = GenericOptions_GetOptionCount(options_Handle, &optionCount);
1668                  if (miResult != MI_RESULT_OK)
1669                      return miResult;
1670              
1671                  for (optionIndex = 0; optionIndex != optionCount; optionIndex++)
1672                  {
1673                      MI_Type optionType;
1674                      const MI_Char *optionName;
1675                      MI_Value optionValue;
1676              
1677                      miResult = MI_Instance_GetElementAt(options_Handle->genericOptions->optionsInstance, optionIndex, &optionName, &optionValue, &optionType, NULL);
1678                      if (miResult != MI_RESULT_OK)
1679                          return miResult;
1680              
1681 krisbash 1.1         switch(optionType)
1682                      {
1683                      case MI_UINT32:
1684                      {
1685                          miResult = destination->ft->SetNumber(destination, optionName, optionValue.uint32, 0);
1686                          break;
1687                      }
1688                      case MI_STRING:
1689                      {
1690                          miResult = destination->ft->SetString(destination, optionName, optionValue.string, 0);
1691                          break;
1692                      }
1693                      case MI_DATETIME:
1694                      {
1695                          if (optionValue.datetime.isTimestamp == MI_TRUE)
1696                              return MI_RESULT_INVALID_PARAMETER;
1697              
1698                          miResult = destination->ft->SetInterval(destination, optionName, &optionValue.datetime.u.interval, 0);
1699                          break;
1700                      }
1701                      default:
1702 krisbash 1.1             return MI_RESULT_INVALID_PARAMETER;
1703                      }
1704                  }
1705              
1706                  /* Migrate credentials */
1707                  miResult = GenericOptions_GetCredentialsCount(options_Handle, &optionCount);
1708                  if (miResult != MI_RESULT_OK)
1709                      return miResult;
1710              
1711                  for (optionIndex = 0; optionIndex != optionCount; optionIndex++)
1712                  {
1713                      const MI_Char *optionName;
1714                      MI_Instance *credInstance;
1715                      MI_UserCredentials credentials;
1716                      MI_Uint32 passwordBufferSize = 0;
1717                      MI_Char *password = NULL;
1718              
1719                      memset(&credentials, 0, sizeof(credentials));
1720              
1721                      miResult = _GetCredentialInstanceAt(options_Handle->genericOptions, optionIndex, &optionName, &credentials.authenticationType, &credInstance);
1722                      if (miResult != MI_RESULT_OK)
1723 krisbash 1.1             return miResult;
1724              
1725                      if ((Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_DIGEST) == 0) ||
1726                               (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_NEGO_WITH_CREDS) == 0) ||
1727                               (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_BASIC) == 0) ||
1728                               (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_KERBEROS) == 0) ||
1729                               (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_NTLM) == 0)
1730              #if (WINVER >= 0x600)
1731                               || (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_CREDSSP) == 0)
1732              #endif
1733                               )
1734                      {
1735                          /* domain/username/password */
1736                          MI_Value tmpValue;
1737                          MI_Type tmpType;
1738                          MI_Uint32 tmpFlags;
1739              
1740                          miResult = MI_Instance_GetElement(credInstance, MI_T("Domain"), &tmpValue, &tmpType, &tmpFlags, NULL);
1741                          if (miResult != MI_RESULT_OK)
1742                          {
1743                              return miResult;
1744 krisbash 1.1             }
1745                          else if (tmpType != MI_STRING)
1746                          {
1747                              return MI_RESULT_INVALID_PARAMETER;
1748                          }
1749                          if (tmpFlags & MI_FLAG_NULL)
1750                          {
1751                              credentials.credentials.usernamePassword.domain = NULL;
1752                          }
1753                          else
1754                          {
1755                              credentials.credentials.usernamePassword.domain = tmpValue.string;
1756                          }
1757              
1758                          miResult = MI_Instance_GetElement(credInstance, MI_T("Username"), &tmpValue, &tmpType, &tmpFlags, NULL);
1759                          if (miResult != MI_RESULT_OK)
1760                          {
1761                              return miResult;
1762                          }
1763                          else if (tmpType != MI_STRING)
1764                          {
1765 krisbash 1.1                 return MI_RESULT_INVALID_PARAMETER;
1766                          }
1767                          if (tmpFlags & MI_FLAG_NULL)
1768                          {
1769                              credentials.credentials.usernamePassword.username = NULL;
1770                          }
1771                          else
1772                          {
1773                              credentials.credentials.usernamePassword.username = tmpValue.string;
1774                          }
1775              
1776                          miResult = MI_Instance_GetElement(credInstance, MI_T("Password"), &tmpValue, &tmpType, &tmpFlags, NULL);
1777                          if (miResult != MI_RESULT_OK)
1778                          {
1779                              return miResult;
1780                          }
1781                          else if (tmpType != MI_UINT8A)
1782                          {
1783                              return MI_RESULT_INVALID_PARAMETER;
1784                          }
1785                          if (tmpFlags & MI_FLAG_NULL)
1786 krisbash 1.1             {
1787                              credentials.credentials.usernamePassword.password = NULL;
1788                          }
1789                          else
1790                          {
1791                              MI_Uint32 bufferNeeded;
1792              
1793                              int decryptRet = DecryptData(tmpValue.uint8a.data, tmpValue.uint8a.size, NULL, 0, &bufferNeeded);
1794                              if (decryptRet != -2)
1795                                  return MI_RESULT_FAILED;
1796              
1797                              password = PAL_Malloc(bufferNeeded);
1798                              if (password == NULL)
1799                                  return MI_RESULT_SERVER_LIMITS_EXCEEDED;
1800              
1801                              passwordBufferSize = bufferNeeded;
1802              
1803                              decryptRet = DecryptData(tmpValue.uint8a.data, tmpValue.uint8a.size, password, passwordBufferSize, &bufferNeeded);
1804                              if (decryptRet != 0)
1805                                  return MI_RESULT_FAILED;
1806              
1807 krisbash 1.1                 credentials.credentials.usernamePassword.password = password;
1808                          }
1809                      }
1810                      else if ((Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_CLIENT_CERTS) == 0) ||
1811                               (Tcscmp(credentials.authenticationType, MI_AUTH_TYPE_ISSUER_CERT) == 0))
1812                      {
1813                          /* Thumbprint */
1814                          MI_Value tmpValue;
1815                          MI_Type tmpType;
1816                          MI_Uint32 tmpFlags;
1817                          miResult = MI_Instance_GetElement(credInstance, MI_T("Thumbprint"), &tmpValue, &tmpType, &tmpFlags, NULL);
1818                          if (miResult != MI_RESULT_OK)
1819                              return miResult;
1820                          if (tmpType != MI_STRING)
1821                              return MI_RESULT_INVALID_PARAMETER;
1822                          credentials.credentials.certificateThumbprint = tmpValue.string;
1823                      }
1824              
1825                      miResult = destination->ft->AddCredentials(destination, optionName, &credentials, 0);
1826                      if (password != NULL)
1827                      {
1828 krisbash 1.1 #if defined(_MSC_VER)
1829                          SecureZeroMemory(password, passwordBufferSize);
1830              #endif
1831                          PAL_Free(password);
1832                      }
1833                      if (miResult != MI_RESULT_OK)
1834                          return miResult;
1835              
1836                  }
1837                  return MI_RESULT_OK;
1838              }
1839              
1840              MI_DestinationOptionsFT g_destinationOptionsFT = 
1841              {
1842                  (void      (MI_CALL *)(_Inout_   MI_DestinationOptions *options)) GenericOptions_Delete,
1843                  (MI_Result (MI_CALL *)(_Inout_   MI_DestinationOptions *options,_In_z_ const MI_Char *optionName,_In_z_ const MI_Char *value,MI_Uint32 flags)) GenericOptions_SetString,
1844                  (MI_Result (MI_CALL *)(_Inout_   MI_DestinationOptions *options,_In_z_ const MI_Char *optionName,_In_   MI_Uint32 value,MI_Uint32 flags)) GenericOptions_SetNumber,
1845                  (MI_Result (MI_CALL *)(_Inout_   MI_DestinationOptions *options,_In_z_ const MI_Char *optionName,_In_   const MI_UserCredentials *credentials,MI_Uint32 flags)) GenericOptions_AddCredentials,
1846                  (MI_Result (MI_CALL *)(_In_      const MI_DestinationOptions *options,_In_z_ const MI_Char *optionName,_Outptr_result_z_ const MI_Char **value,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetString,
1847                  (MI_Result (MI_CALL *)(_In_   const MI_DestinationOptions *options,_In_z_ const MI_Char *optionName,_Out_ MI_Uint32 *value,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetNumber,
1848                  (MI_Result (MI_CALL *)(_In_   const MI_DestinationOptions *options,_Out_ MI_Uint32 *count)) GenericOptions_GetOptionCount,
1849 krisbash 1.1     (MI_Result (MI_CALL *)(_In_   const MI_DestinationOptions *options,MI_Uint32 index,_Outptr_result_z_ const MI_Char **optionName,_Out_ MI_Value *value,_Out_ MI_Type *type,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetOptionAt,
1850                  (MI_Result (MI_CALL *)(_In_   const MI_DestinationOptions *options,_In_z_ const MI_Char *optionName,_Out_ MI_Value *value,_Out_ MI_Type *type,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetOption,
1851                  (MI_Result (MI_CALL *)(_In_   const MI_DestinationOptions *options,_Out_ MI_Uint32 *count)) GenericOptions_GetCredentialsCount,
1852                  (MI_Result (MI_CALL *)(_In_   const MI_DestinationOptions *options,MI_Uint32 index,_Outptr_result_z_ const MI_Char **optionName,_Out_ MI_UserCredentials *credentials,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetCredentialsAt,
1853                  (MI_Result (MI_CALL *)(_In_   const MI_DestinationOptions *options,MI_Uint32 index,_Outptr_result_z_ const MI_Char **optionName,_Out_writes_to_opt_(bufferLength, *passwordLength) MI_Char *password,_In_ MI_Uint32 bufferLength,_Out_ MI_Uint32 *passwordLength,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetCredentialsPasswordAt,
1854                  (MI_Result (MI_CALL *)(_In_ const MI_DestinationOptions* self,_Out_ MI_DestinationOptions* newDestinationOptions)) GenericOptions_Clone,
1855                  (MI_Result (MI_CALL *)(_Inout_   MI_DestinationOptions *options,_In_z_ const MI_Char *optionName,_In_   const MI_Interval *value,MI_Uint32 flags)) GenericOptions_SetInterval,
1856                  (MI_Result (MI_CALL *)(_In_   const MI_DestinationOptions *options,_In_z_ const MI_Char *optionName,_Out_ MI_Interval *value,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetInterval
1857              };
1858              
1859              MI_OperationOptionsFT g_operationOptionsFT =
1860              {
1861                  (void (MI_CALL *)(_Inout_ MI_OperationOptions *options)) GenericOptions_Delete,
1862                  (MI_Result (MI_CALL *)(_Inout_   MI_OperationOptions *options,_In_z_ const MI_Char *optionName,_In_z_ const MI_Char *value,MI_Uint32 flags)) GenericOptions_SetString,
1863                  (MI_Result (MI_CALL *)(_Inout_   MI_OperationOptions *options,_In_z_ const MI_Char *optionName,_In_   MI_Uint32 value,MI_Uint32 flags)) GenericOptions_SetNumber,
1864                  (MI_Result (MI_CALL *)(_Inout_   MI_OperationOptions *options,_In_z_ const MI_Char *optionName,_In_   MI_Type valueType,_In_   const MI_Value *value,MI_Boolean mustComply,MI_Uint32 flags)) GenericOptions_SetCustomOption,
1865                  (MI_Result (MI_CALL *)(_In_   const MI_OperationOptions *options,_In_z_ const MI_Char *optionName,_Outptr_result_z_ const MI_Char **value,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetString,
1866                  (MI_Result (MI_CALL *)(_In_   const MI_OperationOptions *options,_In_z_ const MI_Char *optionName,_Out_ MI_Uint32 *value,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetNumber,
1867                  (MI_Result (MI_CALL *)(_In_   const MI_OperationOptions *options,_Out_ MI_Uint32 *count)) GenericOptions_GetOptionCount,
1868                  (MI_Result (MI_CALL *)(_In_  const  MI_OperationOptions *options,MI_Uint32 index,_Outptr_result_z_ const MI_Char **optionName,_Out_ MI_Value *value,_Out_ MI_Type *type,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetOptionAt,
1869                  (MI_Result (MI_CALL *)(_In_   const MI_OperationOptions *options,_In_z_ const MI_Char *optionName,_Out_ MI_Value *value,_Out_ MI_Type *type,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetOption,
1870 krisbash 1.1     (MI_Result (MI_CALL *)(_In_   const MI_OperationOptions *options,_In_z_ const MI_Char *optionName,_Out_writes_to_opt_(bufferLength, *channelCount) MI_Uint32 *channels,_In_ MI_Uint32 bufferLength,_Out_ MI_Uint32 *channelCount,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetEnabledChannels,
1871                  (MI_Result (MI_CALL *)(_In_ const MI_OperationOptions* self,_Out_ MI_OperationOptions* newOperationOptions)) GenericOptions_Clone,
1872                  (MI_Result (MI_CALL *)(_Inout_   MI_OperationOptions *options,_In_z_ const MI_Char *optionName,_In_   const MI_Interval *value,MI_Uint32 flags)) GenericOptions_SetInterval,
1873                  (MI_Result (MI_CALL *)(_In_   const MI_OperationOptions *options,_In_z_ const MI_Char *optionName,_Out_ MI_Interval *value,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetInterval
1874              };
1875              
1876              MI_SubscriptionDeliveryOptionsFT g_subscriptionDeliveryOptionsFT = 
1877              {
1878                  (MI_Result (MI_CALL *)(_Inout_   MI_SubscriptionDeliveryOptions *options,_In_z_ const MI_Char *optionName,_In_z_ const MI_Char *value,MI_Uint32 flags)) GenericOptions_SetString,
1879                  (MI_Result (MI_CALL *)(_Inout_   MI_SubscriptionDeliveryOptions *options,_In_z_ const MI_Char *optionName,_In_   MI_Uint32 value,MI_Uint32 flags)) GenericOptions_SetNumber,
1880                  (MI_Result (MI_CALL *)(_Inout_   MI_SubscriptionDeliveryOptions *options,_In_z_ const MI_Char *optionName,_In_   const MI_Datetime *value,MI_Uint32 flags)) GenericOptions_SetDateTime,
1881                  (MI_Result (MI_CALL *)(_Inout_   MI_SubscriptionDeliveryOptions *options,_In_z_ const MI_Char *optionName,_In_   const MI_Interval *value,MI_Uint32 flags)) GenericOptions_SetInterval,
1882                  (MI_Result (MI_CALL *)(_Inout_   MI_SubscriptionDeliveryOptions *options,_In_z_ const MI_Char *optionName,_In_   const MI_UserCredentials *credentials,MI_Uint32 flags)) GenericOptions_AddCredentials,
1883                  (MI_Result (MI_CALL *)(_Inout_ MI_SubscriptionDeliveryOptions* self)) GenericOptions_Delete,
1884                  (MI_Result (MI_CALL *)(_In_   const MI_SubscriptionDeliveryOptions *options,_In_z_ const MI_Char *optionName,_Outptr_result_z_ const MI_Char **value,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetString,
1885                  (MI_Result (MI_CALL *)(_In_   const MI_SubscriptionDeliveryOptions *options,_In_z_ const MI_Char *optionName,_Out_ MI_Uint32 *value,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetNumber,
1886                  (MI_Result (MI_CALL *)(_In_   const MI_SubscriptionDeliveryOptions *options,_In_z_ const MI_Char *optionName,_Out_ MI_Datetime *value,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetDateTime,
1887                  (MI_Result (MI_CALL *)(_In_   const MI_SubscriptionDeliveryOptions *options,_In_z_ const MI_Char *optionName,_Out_ MI_Interval *value,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetInterval,
1888                  (MI_Result (MI_CALL *)(_In_   const MI_SubscriptionDeliveryOptions *options,_Out_opt_ MI_Uint32 *count)) GenericOptions_GetOptionCount,
1889                  (MI_Result (MI_CALL *)(_In_   const MI_SubscriptionDeliveryOptions *options,MI_Uint32 index,_Outptr_result_z_ const MI_Char **optionName,_Out_ MI_Value *value,_Out_ MI_Type *type,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetOptionAt,
1890                  (MI_Result (MI_CALL *)(_In_   const MI_SubscriptionDeliveryOptions *options,_In_z_ const MI_Char *optionName,_Out_ MI_Value *value,_Out_ MI_Type *type,_Out_opt_ MI_Uint32 *index,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetOption,
1891 krisbash 1.1     (MI_Result (MI_CALL *)(_In_   const MI_SubscriptionDeliveryOptions *options,_Out_ MI_Uint32 *count)) GenericOptions_GetCredentialsCount,
1892                  (MI_Result (MI_CALL *)(_In_   const MI_SubscriptionDeliveryOptions *options,MI_Uint32 index,_Outptr_result_z_ const MI_Char **optionName,_Out_ MI_UserCredentials *credentials,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetCredentialsAt,
1893                  (MI_Result (MI_CALL *)(_In_   const MI_SubscriptionDeliveryOptions *options,MI_Uint32 index,_Outptr_result_z_ const MI_Char **optionName,_Out_writes_to_opt_(bufferLength, *passwordLength) MI_Char *password,_In_ MI_Uint32 bufferLength,_Out_ MI_Uint32 *passwordLength,_Out_opt_ MI_Uint32 *flags)) GenericOptions_GetCredentialsPasswordAt,
1894                  (MI_Result (MI_CALL *)(_In_ const MI_SubscriptionDeliveryOptions* self,_Out_ MI_SubscriptionDeliveryOptions* newSubscriptionDeliveryOptions)) GenericOptions_Clone
1895              } ;

ViewCVS 0.9.2