~ubuntu-branches/ubuntu/vivid/ndiswrapper/vivid

« back to all changes in this revision

Viewing changes to driver/wrapmem.c

  • Committer: Package Import Robot
  • Author(s): Julian Andres Klode
  • Date: 2012-03-05 16:49:02 UTC
  • mfrom: (1.2.8)
  • Revision ID: package-import@ubuntu.com-20120305164902-rrir76um4yq4eimb
Tags: 1.57-1
* Imported Upstream version 1.57
  - Fixes build with kernel 3.2 (Closes: #655223, LP: #910597)
* Enable hardening build flags (Closes: #655249)
* patches/ndiswrapper-harden.patch: Use $(shell X) instead of `X`
* Update to Policy 3.9.3, copyright-format 1.0

Show diffs side-by-side

added added

removed removed

Lines of Context:
23
23
        size_t size;
24
24
};
25
25
 
 
26
#if ALLOC_DEBUG > 1
26
27
static struct nt_list allocs;
 
28
#endif
 
29
 
27
30
static struct nt_list slack_allocs;
28
31
static spinlock_t alloc_lock;
29
32
 
30
 
struct vmem_block {
31
 
        struct nt_list list;
32
 
        int size;
 
33
#if ALLOC_DEBUG
 
34
const char *alloc_type_name[ALLOC_TYPE_MAX] = {
 
35
        "kmalloc_atomic",
 
36
        "kmalloc_nonatomic",
 
37
        "vmalloc_atomic",
 
38
        "vmalloc_nonatomic",
 
39
        "kmalloc_slack",
 
40
        "pages"
33
41
};
34
42
 
35
 
static struct nt_list vmem_list;
36
 
 
37
 
#if defined(ALLOC_DEBUG)
38
43
struct alloc_info {
39
44
        enum alloc_type type;
40
45
        size_t size;
49
54
static atomic_t alloc_sizes[ALLOC_TYPE_MAX];
50
55
#endif
51
56
 
52
 
void wrapmem_info(void)
53
 
{
54
 
#ifdef ALLOC_DEBUG
55
 
        enum alloc_type type;
56
 
        for (type = 0; type < ALLOC_TYPE_MAX; type++)
57
 
                INFO("total size of allocations in %d: %d",
58
 
                       type, atomic_read(&alloc_sizes[type]));
59
 
#endif
60
 
}
61
 
 
62
57
/* allocate memory and add it to list of allocated pointers; if a
63
58
 * driver doesn't free this memory for any reason (buggy driver or we
64
59
 * allocate space behind driver's back since we need more space than
68
63
void *slack_kmalloc(size_t size)
69
64
{
70
65
        struct slack_alloc_info *info;
71
 
        gfp_t flags;
72
 
 
73
 
        ENTER4("size = %lu", (unsigned long)size);
74
 
 
75
 
        if (irql_gfp() & GFP_ATOMIC)
76
 
                flags = GFP_ATOMIC;
77
 
        else
78
 
                flags = GFP_KERNEL;
79
 
        info = kmalloc(size + sizeof(*info), flags);
 
66
 
 
67
        ENTER4("size = %zu", size);
 
68
        info = kmalloc(size + sizeof(*info), irql_gfp());
80
69
        if (!info)
81
70
                return NULL;
82
71
        info->size = size;
83
72
        spin_lock_bh(&alloc_lock);
84
73
        InsertTailList(&slack_allocs, &info->list);
85
74
        spin_unlock_bh(&alloc_lock);
86
 
#ifdef ALLOC_DEBUG
 
75
#if ALLOC_DEBUG
87
76
        atomic_add(size, &alloc_sizes[ALLOC_TYPE_SLACK]);
88
77
#endif
89
78
        TRACE4("%p, %p", info, info + 1);
100
89
        spin_lock_bh(&alloc_lock);
101
90
        RemoveEntryList(&info->list);
102
91
        spin_unlock_bh(&alloc_lock);
103
 
#ifdef ALLOC_DEBUG
 
92
#if ALLOC_DEBUG
104
93
        atomic_sub(info->size, &alloc_sizes[ALLOC_TYPE_SLACK]);
105
94
#endif
106
95
        kfree(info);
107
96
        EXIT4(return);
108
97
}
109
98
 
110
 
#if defined(ALLOC_DEBUG)
 
99
void *slack_kzalloc(size_t size)
 
100
{
 
101
        void *ptr = slack_kmalloc(size);
 
102
        if (ptr)
 
103
                memset(ptr, 0, size);
 
104
        return ptr;
 
105
}
 
106
 
 
107
#if ALLOC_DEBUG
111
108
void *wrap_kmalloc(size_t size, gfp_t flags, const char *file, int line)
112
109
{
113
110
        struct alloc_info *info;
155
152
        RemoveEntryList(&info->list);
156
153
        spin_unlock_bh(&alloc_lock);
157
154
        if (!(info->type == ALLOC_TYPE_KMALLOC_ATOMIC ||
158
 
              info->type == ALLOC_TYPE_KMALLOC_NON_ATOMIC))
 
155
              info->type == ALLOC_TYPE_KMALLOC_NON_ATOMIC)) {
159
156
                WARNING("invalid type: %d", info->type);
 
157
                return;
 
158
        }
160
159
#endif
161
160
        kfree(info);
162
161
}
218
217
        RemoveEntryList(&info->list);
219
218
        spin_unlock_bh(&alloc_lock);
220
219
        if (!(info->type == ALLOC_TYPE_VMALLOC_ATOMIC ||
221
 
              info->type == ALLOC_TYPE_VMALLOC_NON_ATOMIC))
 
220
              info->type == ALLOC_TYPE_VMALLOC_NON_ATOMIC)) {
222
221
                WARNING("invalid type: %d", info->type);
 
222
                return;
 
223
        }
223
224
#endif
224
225
        vfree(info);
225
226
}
257
258
        spin_lock_bh(&alloc_lock);
258
259
        RemoveEntryList(&info->list);
259
260
        spin_unlock_bh(&alloc_lock);
260
 
        if (info->type != ALLOC_TYPE_PAGES)
 
261
        if (info->type != ALLOC_TYPE_PAGES) {
261
262
                WARNING("invalid type: %d", info->type);
 
263
                return;
 
264
        }
262
265
#endif
263
266
        free_pages((unsigned long)info, get_order(info->size));
264
267
}
270
273
        void *addr;
271
274
        struct alloc_info *info;
272
275
 
273
 
        ENTER4("pool_type: %d, size: %lu, tag: %u", pool_type, size, tag);
 
276
        ENTER4("pool_type: %d, size: %zu, tag: %u", pool_type, size, tag);
274
277
        addr = (ExAllocatePoolWithTag)(pool_type, size, tag);
275
278
        if (!addr)
276
279
                return NULL;
294
297
 
295
298
int wrapmem_init(void)
296
299
{
 
300
#if ALLOC_DEBUG > 1
297
301
        InitializeListHead(&allocs);
 
302
#endif
298
303
        InitializeListHead(&slack_allocs);
299
 
        InitializeListHead(&vmem_list);
300
304
        spin_lock_init(&alloc_lock);
301
305
        return 0;
302
306
}
303
307
 
304
308
void wrapmem_exit(void)
305
309
{
306
 
#ifdef ALLOC_DEBUG
 
310
#if ALLOC_DEBUG
307
311
        enum alloc_type type;
308
312
#endif
309
313
        struct nt_list *ent;
317
321
                if (!ent)
318
322
                        break;
319
323
                info = container_of(ent, struct slack_alloc_info, list);
320
 
#ifdef ALLOC_DEBUG
 
324
#if ALLOC_DEBUG
321
325
                atomic_sub(info->size, &alloc_sizes[ALLOC_TYPE_SLACK]);
322
326
#endif
323
327
                kfree(info);
324
328
        }
325
 
#ifdef ALLOC_DEBUG
 
329
#if ALLOC_DEBUG
326
330
        for (type = 0; type < ALLOC_TYPE_MAX; type++) {
327
331
                int n = atomic_read(&alloc_sizes[type]);
328
332
                if (n)
329
 
                        WARNING("%d bytes of memory in %d leaking", n, type);
 
333
                        WARNING("%d bytes of memory in %s leaking", n,
 
334
                                alloc_type_name[type]);
330
335
        }
331
336
 
332
337
#if ALLOC_DEBUG > 1
340
345
                        break;
341
346
                info = container_of(ent, struct alloc_info, list);
342
347
                atomic_sub(info->size, &alloc_sizes[ALLOC_TYPE_SLACK]);
343
 
                WARNING("%p in %d of size %zu allocated at %s(%d) "
344
 
                        "with tag 0x%08X leaking; freeing it now",
345
 
                        info + 1, info->type, info->size, info->file,
346
 
                        info->line, info->tag);
 
348
                printk(KERN_DEBUG DRIVER_NAME
 
349
                       ": %s:%d leaked %zd bytes at %p (%s, tag 0x%08X)\n",
 
350
                       info->file, info->line, info->size, info + 1,
 
351
                       alloc_type_name[info->type], info->tag);
347
352
                if (info->type == ALLOC_TYPE_KMALLOC_ATOMIC ||
348
353
                    info->type == ALLOC_TYPE_KMALLOC_NON_ATOMIC)
349
354
                        kfree(info);