/mutentca/common/memory.c

https://github.com/vmware/lightwave · C · 636 lines · 508 code · 115 blank · 13 comment · 60 complexity · 9e98e361839c79a08430090fbbf0f72c MD5 · raw file

  1. /*
  2. * Copyright © 2018 VMware, Inc. All Rights Reserved.
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the “License”); you may not
  5. * use this file except in compliance with the License. You may obtain a copy
  6. * of the License at http://www.apache.org/licenses/LICENSE-2.0
  7. *
  8. * Unless required by applicable law or agreed to in writing, software
  9. * distributed under the License is distributed on an “AS IS” BASIS, without
  10. * warranties or conditions of any kind, EITHER EXPRESS OR IMPLIED. See the
  11. * License for the specific language governing permissions and limitations
  12. * under the License.
  13. */
  14. #include "includes.h"
  15. DWORD
  16. LwCAAllocateMemory(
  17. DWORD dwSize,
  18. PVOID * ppMemory
  19. )
  20. {
  21. DWORD dwError = 0;
  22. void* pMemory = NULL;
  23. if (!ppMemory || !dwSize)
  24. {
  25. dwError = LWCA_ERROR_INVALID_PARAMETER;
  26. BAIL_ON_LWCA_ERROR(dwError);
  27. }
  28. pMemory = calloc(1, dwSize);
  29. if (!pMemory)
  30. {
  31. dwError = LWCA_OUT_OF_MEMORY_ERROR;
  32. BAIL_ON_LWCA_ERROR(dwError);
  33. }
  34. cleanup:
  35. *ppMemory = pMemory;
  36. return dwError;
  37. error:
  38. LwCAFreeMemory(pMemory);
  39. pMemory = NULL;
  40. goto cleanup;
  41. }
  42. DWORD
  43. LwCAReallocateMemory(
  44. PVOID pMemory,
  45. PVOID* ppNewMemory,
  46. DWORD dwSize
  47. )
  48. {
  49. DWORD dwError = 0;
  50. void* pNewMemory = NULL;
  51. if (!ppNewMemory)
  52. {
  53. dwError = LWCA_ERROR_INVALID_PARAMETER;
  54. BAIL_ON_LWCA_ERROR(dwError);
  55. }
  56. if (pMemory)
  57. {
  58. pNewMemory = realloc(pMemory, dwSize);
  59. }
  60. else
  61. {
  62. dwError = LwCAAllocateMemory(dwSize, &pNewMemory);
  63. BAIL_ON_LWCA_ERROR(dwError);
  64. }
  65. if (!pNewMemory)
  66. {
  67. dwError = LWCA_OUT_OF_MEMORY_ERROR;
  68. BAIL_ON_LWCA_ERROR(dwError);
  69. }
  70. *ppNewMemory = pNewMemory;
  71. cleanup:
  72. return dwError;
  73. error:
  74. goto cleanup;
  75. }
  76. DWORD
  77. LwCAReallocateMemoryWithInit(
  78. PVOID pMemory,
  79. PVOID* ppNewMemory,
  80. size_t dwNewSize,
  81. size_t dwOldSize
  82. )
  83. {
  84. DWORD dwError = 0;
  85. PVOID pNewMemory = NULL;
  86. if (dwNewSize <= dwOldSize || !ppNewMemory)
  87. {
  88. dwError = LWCA_ERROR_INVALID_PARAMETER;
  89. BAIL_ON_LWCA_ERROR(dwError);
  90. }
  91. dwError = LwCAReallocateMemory(pMemory, &pNewMemory, dwNewSize);
  92. BAIL_ON_LWCA_ERROR(dwError);
  93. memset(((char*)(pNewMemory)) + dwOldSize, 0, dwNewSize - dwOldSize);
  94. *ppNewMemory = pNewMemory;
  95. cleanup:
  96. return dwError;
  97. error:
  98. LWCA_SAFE_FREE_MEMORY(pNewMemory);
  99. goto cleanup;
  100. }
  101. DWORD
  102. LwCACopyMemory(
  103. PVOID pDst,
  104. size_t dstSize,
  105. const void* pSrc,
  106. size_t cpySize
  107. )
  108. {
  109. DWORD dwError = 0;
  110. if (!pDst || !pSrc || cpySize > dstSize)
  111. {
  112. dwError = LWCA_ERROR_INVALID_PARAMETER;
  113. BAIL_ON_LWCA_ERROR(dwError);
  114. }
  115. memcpy(pDst, pSrc, cpySize);
  116. error:
  117. return dwError;
  118. }
  119. DWORD
  120. LwCAAllocateAndCopyMemory(
  121. PVOID pBlob,
  122. size_t iBlobSize,
  123. PVOID* ppOutBlob
  124. )
  125. {
  126. DWORD dwError = 0;
  127. PVOID pMemory = NULL;
  128. if (!pBlob || !ppOutBlob || iBlobSize < 1)
  129. {
  130. dwError = LWCA_ERROR_INVALID_PARAMETER;
  131. BAIL_ON_LWCA_ERROR(dwError);
  132. }
  133. dwError = LwCAAllocateMemory(iBlobSize, &pMemory);
  134. BAIL_ON_LWCA_ERROR(dwError);
  135. dwError = LwCACopyMemory(pMemory, iBlobSize, pBlob, iBlobSize);
  136. BAIL_ON_LWCA_ERROR(dwError);
  137. *ppOutBlob = pMemory;
  138. cleanup:
  139. return dwError;
  140. error:
  141. LWCA_SAFE_FREE_MEMORY(pMemory);
  142. goto cleanup;
  143. }
  144. VOID
  145. LwCAFreeMemory(
  146. PVOID pMemory
  147. )
  148. {
  149. if (pMemory)
  150. {
  151. free(pMemory);
  152. }
  153. return;
  154. }
  155. DWORD
  156. LwCAAllocateStringWithLengthA(
  157. PCSTR pszString,
  158. DWORD dwSize,
  159. PSTR * ppszString
  160. )
  161. {
  162. DWORD dwError = 0;
  163. PSTR pszNewString = NULL;
  164. if (!ppszString || (DWORD)(dwSize + 1) == 0) {
  165. dwError = LWCA_ERROR_INVALID_PARAMETER;
  166. BAIL_ON_LWCA_ERROR(dwError);
  167. }
  168. pszNewString = malloc(dwSize + 1);
  169. if (!pszNewString) {
  170. dwError = LWCA_OUT_OF_MEMORY_ERROR;
  171. BAIL_ON_LWCA_ERROR(dwError);
  172. }
  173. memcpy(pszNewString, pszString, dwSize);
  174. pszNewString[dwSize] = 0;
  175. *ppszString = pszNewString;
  176. cleanup:
  177. return dwError;
  178. error:
  179. goto cleanup;
  180. }
  181. DWORD
  182. LwCAAllocateStringA(
  183. PCSTR pszString,
  184. PSTR * ppszString
  185. )
  186. {
  187. size_t dwLen;
  188. if (!pszString || !ppszString)
  189. {
  190. if (ppszString) { *ppszString = NULL; }
  191. return 0;
  192. }
  193. dwLen = strlen(pszString);
  194. if (dwLen != (DWORD)dwLen) {
  195. return LWCA_ERROR_BUFFER_OVERFLOW;
  196. }
  197. return LwCAAllocateStringWithLengthA(pszString, (DWORD) strlen(pszString), ppszString);
  198. }
  199. DWORD
  200. LwCAAllocateStringPrintfA(
  201. PSTR* ppszString,
  202. PCSTR pszFormat,
  203. ...
  204. )
  205. {
  206. ULONG ulError = 0;
  207. if (!ppszString || !pszFormat)
  208. {
  209. ulError = LWCA_ERROR_INVALID_PARAMETER;
  210. }
  211. else
  212. {
  213. va_list args;
  214. va_start(args, pszFormat);
  215. ulError = LwNtStatusToWin32Error(
  216. LwRtlCStringAllocatePrintfV(
  217. ppszString,
  218. pszFormat,
  219. args));
  220. va_end(args);
  221. }
  222. return ulError;
  223. }
  224. VOID
  225. LwCAFreeStringA(
  226. PSTR pszString
  227. )
  228. {
  229. LwCAFreeMemory(pszString);
  230. }
  231. DWORD
  232. LwCAAllocateStringW(
  233. PCWSTR pwszSrc,
  234. PWSTR* ppwszDst
  235. )
  236. {
  237. DWORD dwError = 0;
  238. if (!pwszSrc || !ppwszDst)
  239. {
  240. dwError = LWCA_ERROR_INVALID_PARAMETER;
  241. }
  242. else
  243. {
  244. dwError = LwNtStatusToWin32Error(
  245. LwRtlWC16StringDuplicate(ppwszDst, pwszSrc));
  246. BAIL_ON_LWCA_ERROR(dwError);
  247. }
  248. error:
  249. return dwError;
  250. }
  251. VOID
  252. LwCAFreeStringW(
  253. PWSTR pszString
  254. )
  255. {
  256. LwCAFreeMemory(pszString);
  257. }
  258. DWORD
  259. ConvertAnsitoUnicodeString(
  260. PCSTR pszSrc,
  261. PWSTR* ppwszDst
  262. )
  263. {
  264. DWORD dwError = 0;
  265. if (!pszSrc || !ppwszDst)
  266. {
  267. dwError = LWCA_ERROR_INVALID_PARAMETER;
  268. }
  269. else
  270. {
  271. dwError = LwNtStatusToWin32Error(
  272. LwRtlWC16StringAllocateFromCString(ppwszDst, pszSrc));
  273. }
  274. return dwError;
  275. }
  276. DWORD
  277. ConvertUnicodetoAnsiString(
  278. PCWSTR pwszSrc,
  279. PSTR* ppszDst
  280. )
  281. {
  282. DWORD dwError = 0;
  283. if (!pwszSrc || !ppszDst)
  284. {
  285. dwError = LWCA_ERROR_INVALID_PARAMETER;
  286. }
  287. else
  288. {
  289. dwError = LwNtStatusToWin32Error(
  290. LwRtlCStringAllocateFromWC16String(ppszDst, pwszSrc));
  291. }
  292. return dwError;
  293. }
  294. DWORD
  295. LwCAGetStringLengthW(
  296. PCWSTR pwszStr,
  297. PSIZE_T pLength
  298. )
  299. {
  300. DWORD dwError = 0;
  301. if (!pwszStr || !pLength)
  302. {
  303. dwError = LWCA_ERROR_INVALID_PARAMETER;
  304. }
  305. else
  306. {
  307. *pLength = LwRtlWC16StringNumChars(pwszStr);
  308. }
  309. return dwError;
  310. }
  311. DWORD
  312. LwCACopyStringArrayA(
  313. PSTR **pppszDst,
  314. DWORD dwDstLen,
  315. PSTR *ppszSrc,
  316. DWORD dwSrcLen
  317. )
  318. {
  319. DWORD dwError = 0;
  320. DWORD dwIdx = 0;
  321. PSTR *ppszDst = NULL;
  322. if (!pppszDst ||
  323. dwDstLen < 1 ||
  324. !ppszSrc ||
  325. dwSrcLen < 1 ||
  326. dwDstLen > dwSrcLen)
  327. {
  328. dwError = LWCA_ERROR_INVALID_PARAMETER;
  329. BAIL_ON_LWCA_ERROR(dwError);
  330. }
  331. dwError = LwCAAllocateMemory(
  332. sizeof(PSTR) * dwDstLen,
  333. (PVOID *)&ppszDst);
  334. BAIL_ON_LWCA_ERROR(dwError);
  335. for (; dwIdx < dwDstLen && dwIdx < dwSrcLen; ++dwIdx)
  336. {
  337. dwError = LwCAAllocateStringA(
  338. ppszSrc[dwIdx],
  339. &ppszDst[dwIdx]);
  340. BAIL_ON_LWCA_ERROR(dwError);
  341. }
  342. *pppszDst = ppszDst;
  343. cleanup:
  344. return dwError;
  345. error:
  346. LwCAFreeStringArrayA(ppszDst, dwDstLen);
  347. if (pppszDst)
  348. {
  349. *pppszDst = NULL;
  350. }
  351. goto cleanup;
  352. }
  353. VOID
  354. LwCAFreeStringArrayA(
  355. PSTR* ppszStrings,
  356. DWORD dwCount
  357. )
  358. {
  359. if (ppszStrings)
  360. {
  361. DWORD dwCnt = 0;
  362. for (dwCnt = 0; dwCnt < dwCount; dwCnt++)
  363. {
  364. if (ppszStrings[dwCnt])
  365. {
  366. LwCAFreeStringA(ppszStrings[dwCnt]);
  367. }
  368. }
  369. LwCAFreeMemory(ppszStrings);
  370. }
  371. }
  372. DWORD
  373. LwCACreateStringArray(
  374. PSTR *ppszSrc,
  375. DWORD dwSrcLen,
  376. PLWCA_STRING_ARRAY* ppStrOutputArray
  377. )
  378. {
  379. DWORD dwError = 0;
  380. DWORD dwIdx = 0;
  381. PLWCA_STRING_ARRAY pStrTempArray = NULL;
  382. if (!ppszSrc || dwSrcLen == 0 || !ppStrOutputArray)
  383. {
  384. dwError = LWCA_ERROR_INVALID_PARAMETER;
  385. BAIL_ON_LWCA_ERROR(dwError);
  386. }
  387. dwError = LwCAAllocateMemory(sizeof(LWCA_STRING_ARRAY), (PVOID*)&pStrTempArray);
  388. BAIL_ON_LWCA_ERROR(dwError);
  389. dwError = LwCAAllocateMemory(sizeof(PSTR) * dwSrcLen, (PVOID*)&pStrTempArray->ppData);
  390. BAIL_ON_LWCA_ERROR(dwError);
  391. for(; dwIdx < dwSrcLen; ++dwIdx)
  392. {
  393. dwError = LwCAAllocateStringA(ppszSrc[dwIdx], &pStrTempArray->ppData[dwIdx]);
  394. BAIL_ON_LWCA_ERROR(dwError);
  395. pStrTempArray->dwCount++;
  396. }
  397. *ppStrOutputArray = pStrTempArray;
  398. cleanup:
  399. return dwError;
  400. error:
  401. LwCAFreeStringArray(pStrTempArray);
  402. if (ppStrOutputArray)
  403. {
  404. *ppStrOutputArray = NULL;
  405. }
  406. goto cleanup;
  407. }
  408. DWORD
  409. LwCACopyStringArray(
  410. PLWCA_STRING_ARRAY pStrInputArray,
  411. PLWCA_STRING_ARRAY* ppStrOutputArray
  412. )
  413. {
  414. DWORD dwError = 0;
  415. DWORD dwIdx = 0;
  416. PLWCA_STRING_ARRAY pStrTempArray = NULL;
  417. if (!pStrInputArray || !pStrInputArray->ppData || pStrInputArray->dwCount == 0 || !ppStrOutputArray)
  418. {
  419. dwError = LWCA_ERROR_INVALID_PARAMETER;
  420. BAIL_ON_LWCA_ERROR(dwError);
  421. }
  422. dwError = LwCAAllocateMemory(sizeof(LWCA_STRING_ARRAY), (PVOID*)&pStrTempArray);
  423. BAIL_ON_LWCA_ERROR(dwError);
  424. dwError = LwCAAllocateMemory(sizeof(PSTR) * pStrInputArray->dwCount, (PVOID*)&pStrTempArray->ppData);
  425. BAIL_ON_LWCA_ERROR(dwError);
  426. for(; dwIdx < pStrInputArray->dwCount; ++dwIdx)
  427. {
  428. dwError = LwCAAllocateStringA(pStrInputArray->ppData[dwIdx], &pStrTempArray->ppData[dwIdx]);
  429. BAIL_ON_LWCA_ERROR(dwError);
  430. pStrTempArray->dwCount++;
  431. }
  432. *ppStrOutputArray = pStrTempArray;
  433. cleanup:
  434. return dwError;
  435. error:
  436. LwCAFreeStringArray(pStrTempArray);
  437. if (ppStrOutputArray)
  438. {
  439. *ppStrOutputArray = NULL;
  440. }
  441. goto cleanup;
  442. }
  443. VOID
  444. LwCAFreeStringArray(
  445. PLWCA_STRING_ARRAY pStrArray
  446. )
  447. {
  448. DWORD dwIdx = 0;
  449. if (pStrArray)
  450. {
  451. if (pStrArray->ppData)
  452. {
  453. for (dwIdx = 0; dwIdx < pStrArray->dwCount; ++dwIdx)
  454. {
  455. LWCA_SAFE_FREE_STRINGA(pStrArray->ppData[dwIdx]);
  456. }
  457. LWCA_SAFE_FREE_MEMORY(pStrArray->ppData);
  458. }
  459. LWCA_SAFE_FREE_MEMORY(pStrArray);
  460. }
  461. }
  462. DWORD
  463. LwCARequestContextCreate(
  464. PLWCA_REQ_CONTEXT *ppReqCtx // OUT
  465. )
  466. {
  467. DWORD dwError = 0;
  468. PLWCA_REQ_CONTEXT pReqCtx = NULL;
  469. if (!ppReqCtx)
  470. {
  471. BAIL_WITH_LWCA_ERROR(dwError, LWCA_ERROR_INVALID_PARAMETER);
  472. }
  473. dwError = LwCAAllocateMemory(sizeof(LWCA_REQ_CONTEXT), (PVOID *)&pReqCtx);
  474. BAIL_ON_LWCA_ERROR(dwError);
  475. *ppReqCtx = pReqCtx;
  476. cleanup:
  477. return dwError;
  478. error:
  479. LwCARequestContextFree(pReqCtx);
  480. if (ppReqCtx)
  481. {
  482. *ppReqCtx = NULL;
  483. }
  484. goto cleanup;
  485. }
  486. VOID
  487. LwCARequestContextFree(
  488. PLWCA_REQ_CONTEXT pReqCtx
  489. )
  490. {
  491. if (pReqCtx)
  492. {
  493. LWCA_SAFE_FREE_STRINGA(pReqCtx->pszBindUPN);
  494. LWCA_SAFE_FREE_STRINGA(pReqCtx->pszBindUPNDN);
  495. LWCA_SAFE_FREE_STRINGA(pReqCtx->pszBindUPNTenant);
  496. LwCAFreeStringArray(pReqCtx->pBindUPNGroups);
  497. LWCA_SAFE_FREE_STRINGA(pReqCtx->pszCAId);
  498. LWCA_SAFE_FREE_STRINGA(pReqCtx->pszRequestId);
  499. LWCA_SAFE_FREE_MEMORY(pReqCtx);
  500. }
  501. }
  502. void
  503. LwCASetBit(unsigned long *flag, int bit)
  504. {
  505. *flag |= 1<< bit;
  506. }
  507. int
  508. LwCAisBitSet(unsigned long flag, int bit)
  509. {
  510. return (flag & ( 1 << bit));
  511. }
  512. void
  513. LwCAClearBit(unsigned long flag, int bit)
  514. {
  515. flag &= ~(1 << bit);
  516. }
  517. void
  518. LwCAToggleBit(unsigned long flag, int bit)
  519. {
  520. flag ^= (1 << bit);
  521. }