]>
Commit | Line | Data |
---|---|---|
30fdf114 | 1 | /* Alloc.c -- Memory allocation functions\r |
c4ab09ef LG |
2 | 2015-02-21 : Igor Pavlov : Public domain */\r |
3 | \r | |
4 | #include "Precomp.h"\r | |
30fdf114 LG |
5 | \r |
6 | #ifdef _WIN32\r | |
7 | #include <windows.h>\r | |
8 | #endif\r | |
9 | #include <stdlib.h>\r | |
10 | \r | |
11 | #include "Alloc.h"\r | |
12 | \r | |
13 | /* #define _SZ_ALLOC_DEBUG */\r | |
14 | \r | |
15 | /* use _SZ_ALLOC_DEBUG to debug alloc/free operations */\r | |
16 | #ifdef _SZ_ALLOC_DEBUG\r | |
17 | #include <stdio.h>\r | |
18 | int g_allocCount = 0;\r | |
19 | int g_allocCountMid = 0;\r | |
20 | int g_allocCountBig = 0;\r | |
21 | #endif\r | |
22 | \r | |
23 | void *MyAlloc(size_t size)\r | |
24 | {\r | |
25 | if (size == 0)\r | |
26 | return 0;\r | |
27 | #ifdef _SZ_ALLOC_DEBUG\r | |
28 | {\r | |
29 | void *p = malloc(size);\r | |
30 | fprintf(stderr, "\nAlloc %10d bytes, count = %10d, addr = %8X", size, g_allocCount++, (unsigned)p);\r | |
31 | return p;\r | |
32 | }\r | |
33 | #else\r | |
34 | return malloc(size);\r | |
35 | #endif\r | |
36 | }\r | |
37 | \r | |
38 | void MyFree(void *address)\r | |
39 | {\r | |
40 | #ifdef _SZ_ALLOC_DEBUG\r | |
41 | if (address != 0)\r | |
42 | fprintf(stderr, "\nFree; count = %10d, addr = %8X", --g_allocCount, (unsigned)address);\r | |
43 | #endif\r | |
44 | free(address);\r | |
45 | }\r | |
46 | \r | |
47 | #ifdef _WIN32\r | |
48 | \r | |
49 | void *MidAlloc(size_t size)\r | |
50 | {\r | |
51 | if (size == 0)\r | |
52 | return 0;\r | |
53 | #ifdef _SZ_ALLOC_DEBUG\r | |
54 | fprintf(stderr, "\nAlloc_Mid %10d bytes; count = %10d", size, g_allocCountMid++);\r | |
55 | #endif\r | |
56 | return VirtualAlloc(0, size, MEM_COMMIT, PAGE_READWRITE);\r | |
57 | }\r | |
58 | \r | |
59 | void MidFree(void *address)\r | |
60 | {\r | |
61 | #ifdef _SZ_ALLOC_DEBUG\r | |
62 | if (address != 0)\r | |
63 | fprintf(stderr, "\nFree_Mid; count = %10d", --g_allocCountMid);\r | |
64 | #endif\r | |
65 | if (address == 0)\r | |
66 | return;\r | |
67 | VirtualFree(address, 0, MEM_RELEASE);\r | |
68 | }\r | |
69 | \r | |
70 | #ifndef MEM_LARGE_PAGES\r | |
71 | #undef _7ZIP_LARGE_PAGES\r | |
72 | #endif\r | |
73 | \r | |
74 | #ifdef _7ZIP_LARGE_PAGES\r | |
75 | SIZE_T g_LargePageSize = 0;\r | |
76 | typedef SIZE_T (WINAPI *GetLargePageMinimumP)();\r | |
77 | #endif\r | |
78 | \r | |
79 | void SetLargePageSize()\r | |
80 | {\r | |
81 | #ifdef _7ZIP_LARGE_PAGES\r | |
82 | SIZE_T size = 0;\r | |
83 | GetLargePageMinimumP largePageMinimum = (GetLargePageMinimumP)\r | |
84 | GetProcAddress(GetModuleHandle(TEXT("kernel32.dll")), "GetLargePageMinimum");\r | |
85 | if (largePageMinimum == 0)\r | |
86 | return;\r | |
87 | size = largePageMinimum();\r | |
88 | if (size == 0 || (size & (size - 1)) != 0)\r | |
89 | return;\r | |
90 | g_LargePageSize = size;\r | |
91 | #endif\r | |
92 | }\r | |
93 | \r | |
94 | \r | |
95 | void *BigAlloc(size_t size)\r | |
96 | {\r | |
97 | if (size == 0)\r | |
98 | return 0;\r | |
99 | #ifdef _SZ_ALLOC_DEBUG\r | |
100 | fprintf(stderr, "\nAlloc_Big %10d bytes; count = %10d", size, g_allocCountBig++);\r | |
101 | #endif\r | |
102 | \r | |
103 | #ifdef _7ZIP_LARGE_PAGES\r | |
104 | if (g_LargePageSize != 0 && g_LargePageSize <= (1 << 30) && size >= (1 << 18))\r | |
105 | {\r | |
106 | void *res = VirtualAlloc(0, (size + g_LargePageSize - 1) & (~(g_LargePageSize - 1)),\r | |
107 | MEM_COMMIT | MEM_LARGE_PAGES, PAGE_READWRITE);\r | |
108 | if (res != 0)\r | |
109 | return res;\r | |
110 | }\r | |
111 | #endif\r | |
112 | return VirtualAlloc(0, size, MEM_COMMIT, PAGE_READWRITE);\r | |
113 | }\r | |
114 | \r | |
115 | void BigFree(void *address)\r | |
116 | {\r | |
117 | #ifdef _SZ_ALLOC_DEBUG\r | |
118 | if (address != 0)\r | |
119 | fprintf(stderr, "\nFree_Big; count = %10d", --g_allocCountBig);\r | |
120 | #endif\r | |
121 | \r | |
122 | if (address == 0)\r | |
123 | return;\r | |
124 | VirtualFree(address, 0, MEM_RELEASE);\r | |
125 | }\r | |
126 | \r | |
127 | #endif\r | |
c4ab09ef LG |
128 | \r |
129 | \r | |
130 | static void *SzAlloc(void *p, size_t size) { UNUSED_VAR(p); return MyAlloc(size); }\r | |
131 | static void SzFree(void *p, void *address) { UNUSED_VAR(p); MyFree(address); }\r | |
132 | ISzAlloc g_Alloc = { SzAlloc, SzFree };\r | |
133 | \r | |
134 | static void *SzBigAlloc(void *p, size_t size) { UNUSED_VAR(p); return BigAlloc(size); }\r | |
135 | static void SzBigFree(void *p, void *address) { UNUSED_VAR(p); BigFree(address); }\r | |
136 | ISzAlloc g_BigAlloc = { SzBigAlloc, SzBigFree };\r |