Subversion Repositories Kolibri OS

Rev

Rev 2187 | Rev 9499 | Go to most recent revision | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 2187 Rev 2216
1
#include 
1
#include 
2
#include 
2
#include 
3
#include 
3
#include 
4
#include 
4
#include 
5
#include 
5
#include 
6
 
6
 
7
#include "acpi.h"
7
#include "acpi.h"
8
#include "acpi_bus.h"
8
#include "acpi_bus.h"
9
#include "dmdev.h"
9
#include "dmdev.h"
10
 
10
 
11
#define PREFIX "ACPI: "
11
#define PREFIX "ACPI: "
12
 
12
 
13
#define ACPI_BUS_CLASS          "system_bus"
13
#define ACPI_BUS_CLASS          "system_bus"
14
#define ACPI_BUS_HID            "KLBSYBUS"
14
#define ACPI_BUS_HID            "KLBSYBUS"
15
#define ACPI_BUS_DEVICE_NAME    "System Bus"
15
#define ACPI_BUS_DEVICE_NAME    "System Bus"
16
 
16
 
17
 
17
 
18
#define ACPI_IS_ROOT_DEVICE(device)    (!(device)->parent)
18
#define ACPI_IS_ROOT_DEVICE(device)    (!(device)->parent)
19
 
19
 
20
LIST_HEAD(acpi_device_list);
20
LIST_HEAD(acpi_device_list);
21
LIST_HEAD(acpi_bus_id_list);
21
LIST_HEAD(acpi_bus_id_list);
22
LIST_HEAD(dmdev_tree);
22
LIST_HEAD(dmdev_tree);
23
 
23
 
24
 
24
 
25
struct acpi_device_bus_id
25
struct acpi_device_bus_id
26
{
26
{
27
    char bus_id[15];
27
    char bus_id[15];
28
    unsigned int instance_no;
28
    unsigned int instance_no;
29
    struct list_head node;
29
    struct list_head node;
30
};
30
};
31
 
31
 
32
 
32
 
33
#define ACPI_NS_ROOT_PATH       "\\"
33
#define ACPI_NS_ROOT_PATH       "\\"
34
#define ACPI_NS_SYSTEM_BUS      "_SB_"
34
#define ACPI_NS_SYSTEM_BUS      "_SB_"
35
 
35
 
36
enum acpi_irq_model_id {
36
enum acpi_irq_model_id {
37
	ACPI_IRQ_MODEL_PIC = 0,
37
	ACPI_IRQ_MODEL_PIC = 0,
38
	ACPI_IRQ_MODEL_IOAPIC,
38
	ACPI_IRQ_MODEL_IOAPIC,
39
	ACPI_IRQ_MODEL_IOSAPIC,
39
	ACPI_IRQ_MODEL_IOSAPIC,
40
	ACPI_IRQ_MODEL_PLATFORM,
40
	ACPI_IRQ_MODEL_PLATFORM,
41
	ACPI_IRQ_MODEL_COUNT
41
	ACPI_IRQ_MODEL_COUNT
42
};
42
};
43
 
43
 
44
enum acpi_bus_removal_type {
44
enum acpi_bus_removal_type {
45
    ACPI_BUS_REMOVAL_NORMAL = 0,
45
    ACPI_BUS_REMOVAL_NORMAL = 0,
46
    ACPI_BUS_REMOVAL_EJECT,
46
    ACPI_BUS_REMOVAL_EJECT,
47
    ACPI_BUS_REMOVAL_SUPRISE,
47
    ACPI_BUS_REMOVAL_SUPRISE,
48
    ACPI_BUS_REMOVAL_TYPE_COUNT
48
    ACPI_BUS_REMOVAL_TYPE_COUNT
49
};
49
};
50
 
50
 
51
 
51
 
52
#define PCI_MAX_DEVICES 32
52
#define PCI_MAX_DEVICES 32
53
#define PCI_MAX_PINS    4
53
#define PCI_MAX_PINS    4
54
 
54
 
55
#define IRQ_TABLE_ENTRIES   (PCI_MAX_DEVICES * PCI_MAX_PINS)
55
#define IRQ_TABLE_ENTRIES   (PCI_MAX_DEVICES * PCI_MAX_PINS)
56
 
56
 
57
static int irqtable[IRQ_TABLE_ENTRIES];
57
static int irqtable[IRQ_TABLE_ENTRIES];
58
static ACPI_HANDLE pci_root_handle;
58
static ACPI_HANDLE pci_root_handle;
59
 
59
 
60
 
60
 
61
#define  addr_offset(addr, off) \
61
#define  addr_offset(addr, off) \
62
    (addr_t)((addr_t)(addr) + (addr_t)(off))
62
    (addr_t)((addr_t)(addr) + (addr_t)(off))
63
 
63
 
64
//#define acpi_remap( addr ) \
64
//#define acpi_remap( addr ) \
65
//    (addr_t)((addr_t)(addr) + OS_BASE)
65
//    (addr_t)((addr_t)(addr) + OS_BASE)
66
 
66
 
67
#define acpi_remap( addr ) MapIoMem((void*)(addr),4096, 0x01)
67
#define acpi_remap( addr ) MapIoMem((void*)(addr),4096, 0x01)
68
 
68
 
69
char* strdup(const char *str);
69
char* strdup(const char *str);
70
 
70
int sprintf(char *buf, const char *fmt, ...);
-
 
71
 
71
void print_pci_irqs();
72
void print_pci_irqs();
72
 
73
 
73
 
74
 
74
struct acpi_device *acpi_root;
75
struct acpi_device *acpi_root;
75
 
76
 
76
extern struct resource iomem_resource;
77
extern struct resource iomem_resource;
77
extern struct resource ioport_resource;
78
extern struct resource ioport_resource;
78
 
79
 
79
enum pic_mode
80
enum pic_mode
80
{
81
{
81
    IO_PIC  = 0,
82
    IO_PIC  = 0,
82
    IO_APIC
83
    IO_APIC
83
};
84
};
84
 
85
 
85
static ACPI_STATUS
86
static ACPI_STATUS
86
resource_to_addr(ACPI_RESOURCE *resource, ACPI_RESOURCE_ADDRESS64 *addr);
87
resource_to_addr(ACPI_RESOURCE *resource, ACPI_RESOURCE_ADDRESS64 *addr);
87
 
88
 
88
static void create_dm_list();
89
static void create_dm_list();
89
 
90
 
90
static void print_dm_list();
91
static void print_dm_list();
91
 
92
 
92
int write_device_dat(char *path);
93
int write_device_dat(char *path);
93
 
94
 
94
 
95
 
95
static void set_pic_mode(enum pic_mode mode)
96
static void set_pic_mode(enum pic_mode mode)
96
{
97
{
97
    ACPI_OBJECT arg1;
98
    ACPI_OBJECT arg1;
98
    ACPI_OBJECT_LIST args;
99
    ACPI_OBJECT_LIST args;
99
    ACPI_STATUS as;
100
    ACPI_STATUS as;
100
 
101
 
101
    arg1.Type = ACPI_TYPE_INTEGER;
102
    arg1.Type = ACPI_TYPE_INTEGER;
102
    arg1.Integer.Value = mode;
103
    arg1.Integer.Value = mode;
103
    args.Count = 1;
104
    args.Count = 1;
104
    args.Pointer = &arg1;
105
    args.Pointer = &arg1;
105
 
106
 
106
    as = AcpiEvaluateObject(ACPI_ROOT_OBJECT, "_PIC", &args, NULL);
107
    as = AcpiEvaluateObject(ACPI_ROOT_OBJECT, "_PIC", &args, NULL);
107
    /*
108
    /*
108
     * We can silently ignore failure as it may not be implemented, ACPI should
109
     * We can silently ignore failure as it may not be implemented, ACPI should
109
     * provide us with correct information anyway
110
     * provide us with correct information anyway
110
     */
111
     */
111
    if (ACPI_SUCCESS(as))
112
    if (ACPI_SUCCESS(as))
112
        dbgprintf(PREFIX "machine set to %s mode\n", mode ? "APIC" : "PIC");
113
        dbgprintf(PREFIX "machine set to %s mode\n", mode ? "APIC" : "PIC");
113
}
114
}
114
 
115
 
115
 
116
 
116
 
117
 
117
static bool pci_use_crs = false;
118
static bool pci_use_crs = false;
118
 
119
 
119
#define IORESOURCE_BUS      0x00001000
120
#define IORESOURCE_BUS      0x00001000
120
 
121
 
121
 
122
 
122
extern struct list_head acpi_pci_roots;
123
extern struct list_head acpi_pci_roots;
123
 
124
 
124
#define ACPI_PCI_ROOT_CLASS     "pci_bridge"
125
#define ACPI_PCI_ROOT_CLASS     "pci_bridge"
125
#define ACPI_PCI_ROOT_DEVICE_NAME   "PCI Root Bridge"
126
#define ACPI_PCI_ROOT_DEVICE_NAME   "PCI Root Bridge"
126
 
127
 
127
static ACPI_STATUS
128
static ACPI_STATUS
128
get_root_bridge_busnr_callback(ACPI_RESOURCE *resource, void *data)
129
get_root_bridge_busnr_callback(ACPI_RESOURCE *resource, void *data)
129
{
130
{
130
    struct resource *res = data;
131
    struct resource *res = data;
131
    ACPI_RESOURCE_ADDRESS64 address;
132
    ACPI_RESOURCE_ADDRESS64 address;
132
 
133
 
133
    if (resource->Type != ACPI_RESOURCE_TYPE_ADDRESS16 &&
134
    if (resource->Type != ACPI_RESOURCE_TYPE_ADDRESS16 &&
134
        resource->Type != ACPI_RESOURCE_TYPE_ADDRESS32 &&
135
        resource->Type != ACPI_RESOURCE_TYPE_ADDRESS32 &&
135
        resource->Type != ACPI_RESOURCE_TYPE_ADDRESS64)
136
        resource->Type != ACPI_RESOURCE_TYPE_ADDRESS64)
136
        return AE_OK;
137
        return AE_OK;
137
 
138
 
138
    AcpiResourceToAddress64(resource, &address);
139
    AcpiResourceToAddress64(resource, &address);
139
    if ((address.AddressLength > 0) &&
140
    if ((address.AddressLength > 0) &&
140
        (address.ResourceType == ACPI_BUS_NUMBER_RANGE)) {
141
        (address.ResourceType == ACPI_BUS_NUMBER_RANGE)) {
141
        res->start = address.Minimum;
142
        res->start = address.Minimum;
142
        res->end = address.Minimum + address.AddressLength - 1;
143
        res->end = address.Minimum + address.AddressLength - 1;
143
    }
144
    }
144
 
145
 
145
    return AE_OK;
146
    return AE_OK;
146
}
147
}
147
 
148
 
148
 
149
 
149
 
150
 
150
static ACPI_STATUS try_get_root_bridge_busnr(ACPI_HANDLE handle,
151
static ACPI_STATUS try_get_root_bridge_busnr(ACPI_HANDLE handle,
151
                         struct resource *res)
152
                         struct resource *res)
152
{
153
{
153
    ACPI_STATUS status;
154
    ACPI_STATUS status;
154
 
155
 
155
    res->start = -1;
156
    res->start = -1;
156
    status =
157
    status =
157
        AcpiWalkResources(handle, METHOD_NAME__CRS,
158
        AcpiWalkResources(handle, METHOD_NAME__CRS,
158
                get_root_bridge_busnr_callback, res);
159
                get_root_bridge_busnr_callback, res);
159
    if (ACPI_FAILURE(status))
160
    if (ACPI_FAILURE(status))
160
        return status;
161
        return status;
161
    if (res->start == -1)
162
    if (res->start == -1)
162
        return AE_ERROR;
163
        return AE_ERROR;
163
    return AE_OK;
164
    return AE_OK;
164
}
165
}
165
 
166
 
166
 
167
 
167
static void acpi_pci_bridge_scan(struct acpi_device *device)
168
static void acpi_pci_bridge_scan(struct acpi_device *device)
168
{
169
{
169
    int status;
170
    int status;
170
    struct acpi_device *child = NULL;
171
    struct acpi_device *child = NULL;
171
 
172
 
172
    if (device->flags.bus_address)
173
    if (device->flags.bus_address)
173
        if (device->parent && device->parent->ops.bind) {
174
        if (device->parent && device->parent->ops.bind) {
174
            status = device->parent->ops.bind(device);
175
            status = device->parent->ops.bind(device);
175
            if (!status) {
176
            if (!status) {
176
                list_for_each_entry(child, &device->children, node)
177
                list_for_each_entry(child, &device->children, node)
177
                    acpi_pci_bridge_scan(child);
178
                    acpi_pci_bridge_scan(child);
178
            }
179
            }
179
        }
180
        }
180
}
181
}
181
 
182
 
182
 
183
 
183
 
184
 
184
struct pci_root_info
185
struct pci_root_info
185
{
186
{
186
    struct acpi_device *bridge;
187
    struct acpi_device *bridge;
187
    char *name;
188
    char *name;
188
    unsigned int res_num;
189
    unsigned int res_num;
189
    struct resource *res;
190
    struct resource *res;
190
    struct pci_bus *bus;
191
    struct pci_bus *bus;
191
    int busnum;
192
    int busnum;
192
};
193
};
193
 
194
 
194
 
195
 
195
static ACPI_STATUS
196
static ACPI_STATUS
196
resource_to_addr(ACPI_RESOURCE *resource, ACPI_RESOURCE_ADDRESS64 *addr)
197
resource_to_addr(ACPI_RESOURCE *resource, ACPI_RESOURCE_ADDRESS64 *addr)
197
{
198
{
198
    ACPI_STATUS status;
199
    ACPI_STATUS status;
199
    struct acpi_resource_memory24 *memory24;
200
    struct acpi_resource_memory24 *memory24;
200
    struct acpi_resource_memory32 *memory32;
201
    struct acpi_resource_memory32 *memory32;
201
    struct acpi_resource_fixed_memory32 *fixed_memory32;
202
    struct acpi_resource_fixed_memory32 *fixed_memory32;
202
 
203
 
203
    memset(addr, 0, sizeof(*addr));
204
    memset(addr, 0, sizeof(*addr));
204
    switch (resource->Type) {
205
    switch (resource->Type) {
205
    case ACPI_RESOURCE_TYPE_MEMORY24:
206
    case ACPI_RESOURCE_TYPE_MEMORY24:
206
        memory24 = &resource->Data.Memory24;
207
        memory24 = &resource->Data.Memory24;
207
        addr->ResourceType = ACPI_MEMORY_RANGE;
208
        addr->ResourceType = ACPI_MEMORY_RANGE;
208
        addr->Minimum = memory24->Minimum;
209
        addr->Minimum = memory24->Minimum;
209
        addr->AddressLength = memory24->AddressLength;
210
        addr->AddressLength = memory24->AddressLength;
210
        addr->Maximum = addr->Minimum + addr->AddressLength - 1;
211
        addr->Maximum = addr->Minimum + addr->AddressLength - 1;
211
        return AE_OK;
212
        return AE_OK;
212
    case ACPI_RESOURCE_TYPE_MEMORY32:
213
    case ACPI_RESOURCE_TYPE_MEMORY32:
213
        memory32 = &resource->Data.Memory32;
214
        memory32 = &resource->Data.Memory32;
214
        addr->ResourceType = ACPI_MEMORY_RANGE;
215
        addr->ResourceType = ACPI_MEMORY_RANGE;
215
        addr->Minimum = memory32->Minimum;
216
        addr->Minimum = memory32->Minimum;
216
        addr->AddressLength = memory32->AddressLength;
217
        addr->AddressLength = memory32->AddressLength;
217
        addr->Maximum = addr->Minimum + addr->AddressLength - 1;
218
        addr->Maximum = addr->Minimum + addr->AddressLength - 1;
218
        return AE_OK;
219
        return AE_OK;
219
    case ACPI_RESOURCE_TYPE_FIXED_MEMORY32:
220
    case ACPI_RESOURCE_TYPE_FIXED_MEMORY32:
220
        fixed_memory32 = &resource->Data.FixedMemory32;
221
        fixed_memory32 = &resource->Data.FixedMemory32;
221
        addr->ResourceType = ACPI_MEMORY_RANGE;
222
        addr->ResourceType = ACPI_MEMORY_RANGE;
222
        addr->Minimum = fixed_memory32->Address;
223
        addr->Minimum = fixed_memory32->Address;
223
        addr->AddressLength = fixed_memory32->AddressLength;
224
        addr->AddressLength = fixed_memory32->AddressLength;
224
        addr->Maximum = addr->Minimum + addr->AddressLength - 1;
225
        addr->Maximum = addr->Minimum + addr->AddressLength - 1;
225
        return AE_OK;
226
        return AE_OK;
226
    case ACPI_RESOURCE_TYPE_ADDRESS16:
227
    case ACPI_RESOURCE_TYPE_ADDRESS16:
227
    case ACPI_RESOURCE_TYPE_ADDRESS32:
228
    case ACPI_RESOURCE_TYPE_ADDRESS32:
228
    case ACPI_RESOURCE_TYPE_ADDRESS64:
229
    case ACPI_RESOURCE_TYPE_ADDRESS64:
229
        status = AcpiResourceToAddress64(resource, addr);
230
        status = AcpiResourceToAddress64(resource, addr);
230
        if (ACPI_SUCCESS(status) &&
231
        if (ACPI_SUCCESS(status) &&
231
            (addr->ResourceType == ACPI_MEMORY_RANGE ||
232
            (addr->ResourceType == ACPI_MEMORY_RANGE ||
232
            addr->ResourceType == ACPI_IO_RANGE) &&
233
            addr->ResourceType == ACPI_IO_RANGE) &&
233
            addr->AddressLength > 0) {
234
            addr->AddressLength > 0) {
234
            return AE_OK;
235
            return AE_OK;
235
        }
236
        }
236
        break;
237
        break;
237
    }
238
    }
238
    return AE_ERROR;
239
    return AE_ERROR;
239
}
240
}
240
 
241
 
241
 
242
 
242
static ACPI_STATUS
243
static ACPI_STATUS
243
count_resource(ACPI_RESOURCE *acpi_res, void *data)
244
count_resource(ACPI_RESOURCE *acpi_res, void *data)
244
{
245
{
245
    struct pci_root_info *info = data;
246
    struct pci_root_info *info = data;
246
    ACPI_RESOURCE_ADDRESS64 addr;
247
    ACPI_RESOURCE_ADDRESS64 addr;
247
    ACPI_STATUS status;
248
    ACPI_STATUS status;
248
 
249
 
249
    status = resource_to_addr(acpi_res, &addr);
250
    status = resource_to_addr(acpi_res, &addr);
250
    if (ACPI_SUCCESS(status))
251
    if (ACPI_SUCCESS(status))
251
        info->res_num++;
252
        info->res_num++;
252
    return AE_OK;
253
    return AE_OK;
253
}
254
}
254
 
255
 
255
 
256
 
256
static ACPI_STATUS setup_resource(ACPI_RESOURCE *acpi_res, void *data)
257
static ACPI_STATUS setup_resource(ACPI_RESOURCE *acpi_res, void *data)
257
{
258
{
258
    struct pci_root_info *info = data;
259
    struct pci_root_info *info = data;
259
    struct resource *res;
260
    struct resource *res;
260
    struct acpi_resource_address64 addr;
261
    struct acpi_resource_address64 addr;
261
    ACPI_STATUS status;
262
    ACPI_STATUS status;
262
    unsigned long flags;
263
    unsigned long flags;
263
    u64 start, end;
264
    u64 start, end;
264
 
265
 
265
    status = resource_to_addr(acpi_res, &addr);
266
    status = resource_to_addr(acpi_res, &addr);
266
    if (!ACPI_SUCCESS(status))
267
    if (!ACPI_SUCCESS(status))
267
        return AE_OK;
268
        return AE_OK;
268
 
269
 
269
    if (addr.ResourceType == ACPI_MEMORY_RANGE)
270
    if (addr.ResourceType == ACPI_MEMORY_RANGE)
270
    {
271
    {
271
        flags = IORESOURCE_MEM;
272
        flags = IORESOURCE_MEM;
272
        if (addr.Info.Mem.Caching == ACPI_PREFETCHABLE_MEMORY)
273
        if (addr.Info.Mem.Caching == ACPI_PREFETCHABLE_MEMORY)
273
            flags |= IORESOURCE_PREFETCH;
274
            flags |= IORESOURCE_PREFETCH;
274
    }
275
    }
275
    else if (addr.ResourceType == ACPI_IO_RANGE)
276
    else if (addr.ResourceType == ACPI_IO_RANGE)
276
    {
277
    {
277
        flags = IORESOURCE_IO;
278
        flags = IORESOURCE_IO;
278
    } else
279
    } else
279
        return AE_OK;
280
        return AE_OK;
280
 
281
 
281
    start = addr.Minimum + addr.TranslationOffset;
282
    start = addr.Minimum + addr.TranslationOffset;
282
    end = addr.Maximum + addr.TranslationOffset;
283
    end = addr.Maximum + addr.TranslationOffset;
283
 
284
 
284
    res = &info->res[info->res_num];
285
    res = &info->res[info->res_num];
285
    res->name = info->name;
286
    res->name = info->name;
286
    res->flags = flags;
287
    res->flags = flags;
287
    res->start = start;
288
    res->start = start;
288
    res->end = end;
289
    res->end = end;
289
    res->child = NULL;
290
    res->child = NULL;
290
 
291
 
291
    if (!pci_use_crs) {
292
    if (!pci_use_crs) {
292
        printk("host bridge window %pR (ignored)\n", res);
293
        printk("host bridge window %pR (ignored)\n", res);
293
        return AE_OK;
294
        return AE_OK;
294
    }
295
    }
295
 
296
 
296
    info->res_num++;
297
    info->res_num++;
297
    if (addr.TranslationOffset)
298
    if (addr.TranslationOffset)
298
        dev_info(NULL, "host bridge window %pR "
299
        dev_info(NULL, "host bridge window %pR "
299
             "(PCI address [%#llx-%#llx])\n",
300
             "(PCI address [%#llx-%#llx])\n",
300
             res, res->start - addr.TranslationOffset,
301
             res, res->start - addr.TranslationOffset,
301
             res->end - addr.TranslationOffset);
302
             res->end - addr.TranslationOffset);
302
    else
303
    else
303
        dev_info(NULL,
304
        dev_info(NULL,
304
             "host bridge window %pR\n", res);
305
             "host bridge window %pR\n", res);
305
 
306
 
306
    return AE_OK;
307
    return AE_OK;
307
}
308
}
308
 
309
 
309
 
310
 
310
 
311
 
311
static void
312
static void
312
get_current_resources(struct acpi_device *device, int busnum,
313
get_current_resources(struct acpi_device *device, int busnum,
313
            int domain, struct pci_bus *bus)
314
            int domain, struct pci_bus *bus)
314
{
315
{
315
    struct pci_root_info info;
316
    struct pci_root_info info;
316
    size_t size;
317
    size_t size;
317
 
318
 
318
    char buf[64];
319
    char buf[64];
319
 
320
 
320
//    if (pci_use_crs)
321
//    if (pci_use_crs)
321
//        pci_bus_remove_resources(bus);
322
//        pci_bus_remove_resources(bus);
322
 
323
 
323
    info.bridge = device;
324
    info.bridge = device;
324
    info.bus = bus;
325
    info.bus = bus;
325
    info.res_num = 0;
326
    info.res_num = 0;
326
    AcpiWalkResources(device->handle, METHOD_NAME__CRS, count_resource,
327
    AcpiWalkResources(device->handle, METHOD_NAME__CRS, count_resource,
327
                &info);
328
                &info);
328
    if (!info.res_num)
329
    if (!info.res_num)
329
        return;
330
        return;
330
 
331
 
331
    size = sizeof(*info.res) * info.res_num;
332
    size = sizeof(*info.res) * info.res_num;
332
    info.res = kmalloc(size, GFP_KERNEL);
333
    info.res = kmalloc(size, GFP_KERNEL);
333
    if (!info.res)
334
    if (!info.res)
334
        goto res_alloc_fail;
335
        goto res_alloc_fail;
335
 
336
 
336
    vsprintf(buf,"PCI Bus %04x:%02x", domain, busnum);
337
    sprintf(buf,"PCI Bus %04x:%02x", domain, busnum);
-
 
338
 
337
    info.name = strdup(buf);
339
    info.name = strdup(buf);
338
 
340
 
339
    if (!info.name)
341
    if (!info.name)
340
        goto name_alloc_fail;
342
        goto name_alloc_fail;
341
 
343
 
342
    info.res_num = 0;
344
    info.res_num = 0;
343
    AcpiWalkResources(device->handle, METHOD_NAME__CRS, setup_resource,
345
    AcpiWalkResources(device->handle, METHOD_NAME__CRS, setup_resource,
344
                &info);
346
                &info);
345
 
347
 
346
    return;
348
    return;
347
 
349
 
348
name_alloc_fail:
350
name_alloc_fail:
349
    kfree(info.res);
351
    kfree(info.res);
350
res_alloc_fail:
352
res_alloc_fail:
351
    return;
353
    return;
352
}
354
}
353
 
355
 
354
 
356
 
355
struct pci_ops pci_root_ops = {
357
struct pci_ops pci_root_ops = {
356
    .read = NULL,
358
    .read = NULL,
357
    .write = NULL,
359
    .write = NULL,
358
};
360
};
359
 
361
 
360
 
362
 
361
struct pci_bus*  pci_acpi_scan_root(struct acpi_pci_root *root)
363
struct pci_bus*  pci_acpi_scan_root(struct acpi_pci_root *root)
362
{
364
{
363
    struct acpi_device *device = root->device;
365
    struct acpi_device *device = root->device;
364
    int domain = root->segment;
366
    int domain = root->segment;
365
    int busnum = root->secondary.start;
367
    int busnum = root->secondary.start;
366
    struct pci_bus *bus;
368
    struct pci_bus *bus;
367
    struct pci_sysdata *sd;
369
    struct pci_sysdata *sd;
368
	int node = 0;
370
	int node = 0;
369
 
371
 
370
    if (domain ) {
372
    if (domain ) {
371
        printk(KERN_WARNING "pci_bus %04x:%02x: "
373
        printk(KERN_WARNING "pci_bus %04x:%02x: "
372
               "ignored (multiple domains not supported)\n",
374
               "ignored (multiple domains not supported)\n",
373
               domain, busnum);
375
               domain, busnum);
374
        return NULL;
376
        return NULL;
375
    }
377
    }
376
 
378
 
377
	node = -1;
379
	node = -1;
378
    /* Allocate per-root-bus (not per bus) arch-specific data.
380
    /* Allocate per-root-bus (not per bus) arch-specific data.
379
     * TODO: leak; this memory is never freed.
381
     * TODO: leak; this memory is never freed.
380
     * It's arguable whether it's worth the trouble to care.
382
     * It's arguable whether it's worth the trouble to care.
381
     */
383
     */
382
    sd = kzalloc(sizeof(*sd), GFP_KERNEL);
384
    sd = kzalloc(sizeof(*sd), GFP_KERNEL);
383
    if (!sd) {
385
    if (!sd) {
384
        printk(KERN_WARNING "pci_bus %04x:%02x: "
386
        printk(KERN_WARNING "pci_bus %04x:%02x: "
385
               "ignored (out of memory)\n", domain, busnum);
387
               "ignored (out of memory)\n", domain, busnum);
386
        return NULL;
388
        return NULL;
387
    }
389
    }
388
 
390
 
389
    sd->domain = domain;
391
    sd->domain = domain;
390
    sd->node = node;
392
    sd->node = node;
391
    /*
393
    /*
392
     * Maybe the desired pci bus has been already scanned. In such case
394
     * Maybe the desired pci bus has been already scanned. In such case
393
     * it is unnecessary to scan the pci bus with the given domain,busnum.
395
     * it is unnecessary to scan the pci bus with the given domain,busnum.
394
     */
396
     */
395
    bus = pci_find_bus(domain, busnum);
397
    bus = pci_find_bus(domain, busnum);
396
    if (bus) {
398
    if (bus) {
397
        /*
399
        /*
398
         * If the desired bus exits, the content of bus->sysdata will
400
         * If the desired bus exits, the content of bus->sysdata will
399
         * be replaced by sd.
401
         * be replaced by sd.
400
         */
402
         */
401
        memcpy(bus->sysdata, sd, sizeof(*sd));
403
        memcpy(bus->sysdata, sd, sizeof(*sd));
402
        kfree(sd);
404
        kfree(sd);
403
    } else {
405
    } else {
404
        bus = pci_create_bus(busnum, &pci_root_ops, sd);
406
        bus = pci_create_bus(busnum, &pci_root_ops, sd);
405
        if (bus) {
407
        if (bus) {
406
            get_current_resources(device, busnum, domain, bus);
408
            get_current_resources(device, busnum, domain, bus);
407
            bus->subordinate = pci_scan_child_bus(bus);
409
            bus->subordinate = pci_scan_child_bus(bus);
408
        }
410
        }
409
    }
411
    }
410
 
412
 
411
    if (!bus)
413
    if (!bus)
412
        kfree(sd);
414
        kfree(sd);
413
 
415
 
414
    if (bus && node != -1) {
416
    if (bus && node != -1) {
415
        printk("on NUMA node %d\n", node);
417
        printk("on NUMA node %d\n", node);
416
    }
418
    }
417
 
419
 
418
    return bus;
420
    return bus;
419
}
421
}
420
 
422
 
421
 
423
 
422
 
424
 
423
static int acpi_pci_root_add(struct acpi_device *device)
425
static int acpi_pci_root_add(struct acpi_device *device)
424
{
426
{
425
    unsigned long long segment, bus;
427
    unsigned long long segment, bus;
426
    ACPI_STATUS status;
428
    ACPI_STATUS status;
427
    int result;
429
    int result;
428
    struct acpi_pci_root *root;
430
    struct acpi_pci_root *root;
429
    ACPI_HANDLE handle;
431
    ACPI_HANDLE handle;
430
    struct acpi_device *child;
432
    struct acpi_device *child;
431
    u32 flags, base_flags;
433
    u32 flags, base_flags;
432
 
434
 
433
    root = kzalloc(sizeof(struct acpi_pci_root), GFP_KERNEL);
435
    root = kzalloc(sizeof(struct acpi_pci_root), GFP_KERNEL);
434
    if (!root)
436
    if (!root)
435
        return -ENOMEM;
437
        return -ENOMEM;
436
 
438
 
437
    segment = 0;
439
    segment = 0;
438
    status = acpi_evaluate_integer(device->handle, METHOD_NAME__SEG, NULL,
440
    status = acpi_evaluate_integer(device->handle, METHOD_NAME__SEG, NULL,
439
                       &segment);
441
                       &segment);
440
    if (ACPI_FAILURE(status) && status != AE_NOT_FOUND) {
442
    if (ACPI_FAILURE(status) && status != AE_NOT_FOUND) {
441
        printk(KERN_ERR PREFIX "can't evaluate _SEG\n");
443
        printk(KERN_ERR PREFIX "can't evaluate _SEG\n");
442
        result = -ENODEV;
444
        result = -ENODEV;
443
        goto end;
445
        goto end;
444
    }
446
    }
445
 
447
 
446
    /* Check _CRS first, then _BBN.  If no _BBN, default to zero. */
448
    /* Check _CRS first, then _BBN.  If no _BBN, default to zero. */
447
    root->secondary.flags = IORESOURCE_BUS;
449
    root->secondary.flags = IORESOURCE_BUS;
448
    status = try_get_root_bridge_busnr(device->handle, &root->secondary);
450
    status = try_get_root_bridge_busnr(device->handle, &root->secondary);
449
    if (ACPI_FAILURE(status))
451
    if (ACPI_FAILURE(status))
450
    {
452
    {
451
        /*
453
        /*
452
         * We need both the start and end of the downstream bus range
454
         * We need both the start and end of the downstream bus range
453
         * to interpret _CBA (MMCONFIG base address), so it really is
455
         * to interpret _CBA (MMCONFIG base address), so it really is
454
         * supposed to be in _CRS.  If we don't find it there, all we
456
         * supposed to be in _CRS.  If we don't find it there, all we
455
         * can do is assume [_BBN-0xFF] or [0-0xFF].
457
         * can do is assume [_BBN-0xFF] or [0-0xFF].
456
         */
458
         */
457
        root->secondary.end = 0xFF;
459
        root->secondary.end = 0xFF;
458
        printk(KERN_WARNING PREFIX
460
        printk(KERN_WARNING PREFIX
459
               "no secondary bus range in _CRS\n");
461
               "no secondary bus range in _CRS\n");
460
        status = acpi_evaluate_integer(device->handle, METHOD_NAME__BBN,                           NULL, &bus);
462
        status = acpi_evaluate_integer(device->handle, METHOD_NAME__BBN,                           NULL, &bus);
461
        if (ACPI_SUCCESS(status))
463
        if (ACPI_SUCCESS(status))
462
            root->secondary.start = bus;
464
            root->secondary.start = bus;
463
        else if (status == AE_NOT_FOUND)
465
        else if (status == AE_NOT_FOUND)
464
            root->secondary.start = 0;
466
            root->secondary.start = 0;
465
        else {
467
        else {
466
            printk(KERN_ERR PREFIX "can't evaluate _BBN\n");
468
            printk(KERN_ERR PREFIX "can't evaluate _BBN\n");
467
            result = -ENODEV;
469
            result = -ENODEV;
468
            goto end;
470
            goto end;
469
        }
471
        }
470
    }
472
    }
471
 
473
 
472
    INIT_LIST_HEAD(&root->node);
474
    INIT_LIST_HEAD(&root->node);
473
    root->device = device;
475
    root->device = device;
474
    root->segment = segment & 0xFFFF;
476
    root->segment = segment & 0xFFFF;
475
    strcpy(acpi_device_name(device), ACPI_PCI_ROOT_DEVICE_NAME);
477
    strcpy(acpi_device_name(device), ACPI_PCI_ROOT_DEVICE_NAME);
476
    strcpy(acpi_device_class(device), ACPI_PCI_ROOT_CLASS);
478
    strcpy(acpi_device_class(device), ACPI_PCI_ROOT_CLASS);
477
    device->driver_data = root;
479
    device->driver_data = root;
478
 
480
 
479
    /*
481
    /*
480
     * All supported architectures that use ACPI have support for
482
     * All supported architectures that use ACPI have support for
481
     * PCI domains, so we indicate this in _OSC support capabilities.
483
     * PCI domains, so we indicate this in _OSC support capabilities.
482
     */
484
     */
483
//    flags = base_flags = OSC_PCI_SEGMENT_GROUPS_SUPPORT;
485
//    flags = base_flags = OSC_PCI_SEGMENT_GROUPS_SUPPORT;
484
//    acpi_pci_osc_support(root, flags);
486
//    acpi_pci_osc_support(root, flags);
485
 
487
 
486
    /*
488
    /*
487
     * TBD: Need PCI interface for enumeration/configuration of roots.
489
     * TBD: Need PCI interface for enumeration/configuration of roots.
488
     */
490
     */
489
 
491
 
490
    /* TBD: Locking */
492
    /* TBD: Locking */
491
    list_add_tail(&root->node, &acpi_pci_roots);
493
    list_add_tail(&root->node, &acpi_pci_roots);
492
 
494
 
493
    printk(KERN_INFO PREFIX "%s [%s] (domain %04x %pR)\n",
495
    printk(KERN_INFO PREFIX "%s [%s] (domain %04x %pR)\n",
494
           acpi_device_name(device), acpi_device_bid(device),
496
           acpi_device_name(device), acpi_device_bid(device),
495
           root->segment, &root->secondary);
497
           root->segment, &root->secondary);
496
 
498
 
497
    /*
499
    /*
498
     * Scan the Root Bridge
500
     * Scan the Root Bridge
499
     * --------------------
501
     * --------------------
500
     * Must do this prior to any attempt to bind the root device, as the
502
     * Must do this prior to any attempt to bind the root device, as the
501
     * PCI namespace does not get created until this call is made (and
503
     * PCI namespace does not get created until this call is made (and
502
     * thus the root bridge's pci_dev does not exist).
504
     * thus the root bridge's pci_dev does not exist).
503
     */
505
     */
504
 
506
 
505
    root->bus = pci_acpi_scan_root(root);
507
    root->bus = pci_acpi_scan_root(root);
506
    if (!root->bus) {
508
    if (!root->bus) {
507
        printk(KERN_ERR PREFIX
509
        printk(KERN_ERR PREFIX
508
                "Bus %04x:%02x not present in PCI namespace\n",
510
                "Bus %04x:%02x not present in PCI namespace\n",
509
                root->segment, (unsigned int)root->secondary.start);
511
                root->segment, (unsigned int)root->secondary.start);
510
        result = -ENODEV;
512
        result = -ENODEV;
511
        goto end;
513
        goto end;
512
    }
514
    }
513
 
515
 
514
    /*
516
    /*
515
     * Attach ACPI-PCI Context
517
     * Attach ACPI-PCI Context
516
     * -----------------------
518
     * -----------------------
517
     * Thus binding the ACPI and PCI devices.
519
     * Thus binding the ACPI and PCI devices.
518
     */
520
     */
519
    result = acpi_pci_bind_root(device);
521
    result = acpi_pci_bind_root(device);
520
    if (result)
522
    if (result)
521
        goto end;
523
        goto end;
522
 
524
 
523
    /*
525
    /*
524
     * PCI Routing Table
526
     * PCI Routing Table
525
     * -----------------
527
     * -----------------
526
     * Evaluate and parse _PRT, if exists.
528
     * Evaluate and parse _PRT, if exists.
527
     */
529
     */
528
    status = AcpiGetHandle(device->handle, METHOD_NAME__PRT, &handle);
530
    status = AcpiGetHandle(device->handle, METHOD_NAME__PRT, &handle);
529
    if (ACPI_SUCCESS(status))
531
    if (ACPI_SUCCESS(status))
530
        result = acpi_pci_irq_add_prt(device->handle, root->bus);
532
        result = acpi_pci_irq_add_prt(device->handle, root->bus);
531
 
533
 
532
    /*
534
    /*
533
     * Scan and bind all _ADR-Based Devices
535
     * Scan and bind all _ADR-Based Devices
534
     */
536
     */
535
    list_for_each_entry(child, &device->children, node)
537
    list_for_each_entry(child, &device->children, node)
536
        acpi_pci_bridge_scan(child);
538
        acpi_pci_bridge_scan(child);
537
 
539
 
538
    return 0;
540
    return 0;
539
 
541
 
540
end:
542
end:
541
    if (!list_empty(&root->node))
543
    if (!list_empty(&root->node))
542
        list_del(&root->node);
544
        list_del(&root->node);
543
    kfree(root);
545
    kfree(root);
544
    return result;
546
    return result;
545
}
547
}
546
 
548
 
547
 
549
 
548
static const struct acpi_device_ids root_device_ids[] =
550
static const struct acpi_device_ids root_device_ids[] =
549
{
551
{
550
    {"PNP0A03", 0},
552
    {"PNP0A03", 0},
551
    {"",        0},
553
    {"",        0},
552
};
554
};
553
 
555
 
554
void acpi_init_pci(struct acpi_device *device)
556
void acpi_init_pci(struct acpi_device *device)
555
{
557
{
556
    struct acpi_device *child;
558
    struct acpi_device *child;
557
 
559
 
558
    if ( !acpi_match_device_ids(device, root_device_ids) )
560
    if ( !acpi_match_device_ids(device, root_device_ids) )
559
    {
561
    {
560
        dbgprintf(PREFIX "PCI root %s\n", device->pnp.bus_id);
562
        dbgprintf(PREFIX "PCI root %s\n", device->pnp.bus_id);
561
        acpi_pci_root_add(device);
563
        acpi_pci_root_add(device);
562
    };
564
    };
563
 
565
 
564
    list_for_each_entry(child, &device->children, node)
566
    list_for_each_entry(child, &device->children, node)
565
    {
567
    {
566
        acpi_init_pci(child);
568
        acpi_init_pci(child);
567
    };
569
    };
568
 
570
 
569
};
571
};
570
 
572
 
571
 
573
 
572
u32_t drvEntry(int action, char *cmdline)
574
u32_t drvEntry(int action, char *cmdline)
573
{
575
{
574
    u32_t retval;
576
    u32_t retval;
575
 
577
 
576
    ACPI_STATUS status;
578
    ACPI_STATUS status;
577
 
579
 
578
    int i;
580
    int i;
579
 
581
 
580
    if(action != 1)
582
    if(action != 1)
581
        return 0;
583
        return 0;
582
 
584
 
583
    if( !dbg_open("/rd/1/drivers/acpi.log") )
585
    if( !dbg_open("/rd/1/drivers/acpi.log") )
584
    {
586
    {
585
        printf("Can't open /rd/1/drivers/acpi.log\nExit\n");
587
        printf("Can't open /rd/1/drivers/acpi.log\nExit\n");
586
        return 0;
588
        return 0;
587
    }
589
    }
588
 
590
 
589
    status = AcpiReallocateRootTable();
-
 
590
    if (ACPI_FAILURE(status)) {
-
 
591
        dbgprintf("Unable to reallocate ACPI tables\n");
-
 
592
        goto err;
-
 
593
    }
-
 
594
 
-
 
595
    status = AcpiInitializeSubsystem();
591
    status = AcpiInitializeSubsystem();
596
    if (status != AE_OK) {
592
    if (status != AE_OK) {
597
          dbgprintf("AcpiInitializeSubsystem failed (%s)\n",
593
          dbgprintf("AcpiInitializeSubsystem failed (%s)\n",
598
                     AcpiFormatException(status));
594
                     AcpiFormatException(status));
599
          goto err;
595
          goto err;
600
    }
596
    }
601
 
597
 
602
    status = AcpiInitializeTables(NULL, 0, TRUE);
598
    status = AcpiInitializeTables (NULL, 16, FALSE);
603
    if (status != AE_OK) {
599
    if (status != AE_OK) {
604
          dbgprintf("AcpiInitializeTables failed (%s)\n",
600
          dbgprintf("AcpiInitializeTables failed (%s)\n",
605
                     AcpiFormatException(status));
601
                     AcpiFormatException(status));
606
          goto err;
602
          goto err;
607
    }
603
    }
608
 
604
 
609
    status = AcpiLoadTables();
605
    status = AcpiLoadTables();
610
    if (status != AE_OK) {
606
    if (status != AE_OK) {
611
          dbgprintf("AcpiLoadTables failed (%s)\n",
607
          dbgprintf("AcpiLoadTables failed (%s)\n",
612
                     AcpiFormatException(status));
608
                     AcpiFormatException(status));
613
          goto err;
609
          goto err;
614
    }
610
    }
615
 
611
 
616
//    u32_t mode = ACPI_NO_HARDWARE_INIT | ACPI_NO_ACPI_ENABLE;
612
//    u32_t mode = ACPI_NO_HARDWARE_INIT | ACPI_NO_ACPI_ENABLE;
617
 
613
 
618
    status = AcpiEnableSubsystem(ACPI_NO_HANDLER_INIT | ACPI_NO_HARDWARE_INIT);
614
    status = AcpiEnableSubsystem(ACPI_NO_HANDLER_INIT | ACPI_NO_HARDWARE_INIT);
619
    if (status != AE_OK) {
615
    if (status != AE_OK) {
620
        dbgprintf("AcpiEnableSubsystem failed (%s)\n",
616
        dbgprintf("AcpiEnableSubsystem failed (%s)\n",
621
            AcpiFormatException(status));
617
            AcpiFormatException(status));
622
        goto err;
618
        goto err;
623
    }
619
    }
624
 
620
 
625
    status = AcpiInitializeObjects (ACPI_FULL_INITIALIZATION);
621
    status = AcpiInitializeObjects (ACPI_FULL_INITIALIZATION);
626
    if (ACPI_FAILURE (status))
622
    if (ACPI_FAILURE (status))
627
    {
623
    {
628
        dbgprintf("AcpiInitializeObjects failed (%s)\n",
624
        dbgprintf("AcpiInitializeObjects failed (%s)\n",
629
            AcpiFormatException(status));
625
            AcpiFormatException(status));
630
        goto err;
626
        goto err;
631
    }
627
    }
632
 
628
 
633
 
629
 
634
    set_pic_mode(IO_APIC);
630
    set_pic_mode(IO_APIC);
635
 
631
 
636
    acpi_scan();
632
    acpi_scan();
637
 
633
 
638
    acpi_init_pci(acpi_root);
634
    acpi_init_pci(acpi_root);
639
 
635
 
640
    print_pci_irqs();
636
    print_pci_irqs();
641
 
637
 
642
    create_dm_list();
638
    create_dm_list();
643
 
639
 
644
    print_dm_list();
640
    print_dm_list();
645
 
641
 
646
    write_device_dat("/RD/1/DRIVERS/DEVICES.DAT");
642
    write_device_dat("/RD/1/DRIVERS/DEVICES.DAT");
647
 
643
 
648
err:
644
err:
649
 
645
 
650
    return 0;
646
    return 0;
651
 
647
 
652
};
648
};
653
 
649
 
654
char* strdup(const char *str)
650
char* strdup(const char *str)
655
{
651
{
656
    size_t len = strlen (str) + 1;
652
    size_t len = strlen (str) + 1;
657
    char *copy = malloc(len);
653
    char *copy = malloc(len);
658
    if (copy)
654
    if (copy)
659
    {
655
    {
660
        memcpy (copy, str, len);
656
        memcpy (copy, str, len);
661
    }
657
    }
662
    return copy;
658
    return copy;
663
}
659
}
664
 
660
 
665
 
661
 
666
static void dm_add_pci_bus(struct pci_bus *bus)
662
static void dm_add_pci_bus(struct pci_bus *bus)
667
{
663
{
668
    struct pci_bus *tbus;
664
    struct pci_bus *tbus;
669
    struct pci_dev *dev;
665
    struct pci_dev *dev;
670
    dmdev_t        *dmdev;
666
    dmdev_t        *dmdev;
671
 
667
 
672
    dmdev = (dmdev_t*)kzalloc(sizeof(dmdev_t),GFP_KERNEL);
668
    dmdev = (dmdev_t*)kzalloc(sizeof(dmdev_t),GFP_KERNEL);
673
 
669
 
674
//    INIT_LIST_HEAD(&dmdev->list);
670
//    INIT_LIST_HEAD(&dmdev->list);
675
//    dmdev->type = 1;
671
//    dmdev->type = 1;
676
//    dmdev->acpi_dev = bus->self->acpi_dev;
672
//    dmdev->acpi_dev = bus->self->acpi_dev;
677
//    dmdev->pci_dev = bus->self;
673
//    dmdev->pci_dev = bus->self;
678
//    list_add_tail(&dmdev->list, &dmdev_tree);
674
//    list_add_tail(&dmdev->list, &dmdev_tree);
679
 
675
 
680
    list_for_each_entry(dev, &bus->devices, bus_list)
676
    list_for_each_entry(dev, &bus->devices, bus_list)
681
    {
677
    {
682
        dmdev = (dmdev_t*)kzalloc(sizeof(dmdev_t),GFP_KERNEL);
678
        dmdev = (dmdev_t*)kzalloc(sizeof(dmdev_t),GFP_KERNEL);
683
 
679
 
684
        INIT_LIST_HEAD(&dmdev->list);
680
        INIT_LIST_HEAD(&dmdev->list);
685
        dmdev->type = 1;
681
        dmdev->type = 1;
686
        dmdev->acpi_dev = dev->acpi_dev;
682
        dmdev->acpi_dev = dev->acpi_dev;
687
        dmdev->pci_dev = dev;
683
        dmdev->pci_dev = dev;
688
        list_add_tail(&dmdev->list, &dmdev_tree);
684
        list_add_tail(&dmdev->list, &dmdev_tree);
689
    };
685
    };
690
 
686
 
691
    list_for_each_entry(tbus, &bus->children, node)
687
    list_for_each_entry(tbus, &bus->children, node)
692
    {
688
    {
693
        dm_add_pci_bus(tbus);
689
        dm_add_pci_bus(tbus);
694
    };
690
    };
695
 
691
 
696
};
692
};
697
 
693
 
698
static ACPI_STATUS
694
static ACPI_STATUS
699
count_dev_resources(ACPI_RESOURCE *acpi_res, void *data)
695
count_dev_resources(ACPI_RESOURCE *acpi_res, void *data)
700
{
696
{
701
    (*(int*)data)++;
697
    (*(int*)data)++;
702
    return AE_OK;
698
    return AE_OK;
703
}
699
}
704
 
700
 
705
 
701
 
706
static void dm_add_acpi(struct acpi_device *device)
702
static void dm_add_acpi(struct acpi_device *device)
707
{
703
{
708
    struct acpi_device *child;
704
    struct acpi_device *child;
709
    ACPI_DEVICE_INFO *info = NULL;
705
    ACPI_DEVICE_INFO *info = NULL;
710
    ACPI_STATUS status;
706
    ACPI_STATUS status;
711
 
707
 
712
    dmdev_t  *dmdev;
708
    dmdev_t  *dmdev;
713
    uint32_t  res_num = 0;
709
    uint32_t  res_num = 0;
714
 
710
 
715
    status = AcpiGetObjectInfo(device->handle, &info);
711
    status = AcpiGetObjectInfo(device->handle, &info);
716
 
712
 
717
    if ( (status == AE_OK) && (info->Valid & ACPI_VALID_HID))
713
    if ( (status == AE_OK) && (info->Valid & ACPI_VALID_HID))
718
    {
714
    {
719
        if( strcmp(info->HardwareId.String,"PNP0C0F") == 0)
715
        if( strcmp(info->HardwareId.String,"PNP0C0F") == 0)
720
        {
716
        {
721
            kfree(info);
717
            kfree(info);
722
            return;
718
            return;
723
        };
719
        };
724
    };
720
    };
725
 
721
 
726
    kfree(info);
722
    kfree(info);
727
 
723
 
728
    if(device->pci_dev == NULL)
724
    if(device->pci_dev == NULL)
729
    {
725
    {
730
        AcpiWalkResources(device->handle, METHOD_NAME__CRS,
726
        AcpiWalkResources(device->handle, METHOD_NAME__CRS,
731
                          count_dev_resources, &res_num);
727
                          count_dev_resources, &res_num);
732
 
728
 
733
        if(res_num != 0)
729
        if(res_num != 0)
734
        {
730
        {
735
            dmdev = (dmdev_t*)kzalloc(sizeof(dmdev_t),GFP_KERNEL);
731
            dmdev = (dmdev_t*)kzalloc(sizeof(dmdev_t),GFP_KERNEL);
736
 
732
 
737
            INIT_LIST_HEAD(&dmdev->list);
733
            INIT_LIST_HEAD(&dmdev->list);
738
            dmdev->type = 0;
734
            dmdev->type = 0;
739
            dmdev->acpi_dev = device;
735
            dmdev->acpi_dev = device;
740
            dmdev->pci_dev = NULL;
736
            dmdev->pci_dev = NULL;
741
            list_add_tail(&dmdev->list, &dmdev_tree);
737
            list_add_tail(&dmdev->list, &dmdev_tree);
742
        };
738
        };
743
    };
739
    };
744
    list_for_each_entry(child, &device->children, node)
740
    list_for_each_entry(child, &device->children, node)
745
    {
741
    {
746
        dm_add_acpi(child);
742
        dm_add_acpi(child);
747
    };
743
    };
748
};
744
};
749
 
745
 
750
static void create_dm_list()
746
static void create_dm_list()
751
{
747
{
752
    struct acpi_pci_root *root;
748
    struct acpi_pci_root *root;
753
 
749
 
754
 
750
 
755
    list_for_each_entry(root, &acpi_pci_roots, node)
751
    list_for_each_entry(root, &acpi_pci_roots, node)
756
    {
752
    {
757
        struct pci_bus *pbus, *tbus;
753
        struct pci_bus *pbus, *tbus;
758
        struct pci_dev *dev;
754
        struct pci_dev *dev;
759
 
755
 
760
        pbus = root->bus;
756
        pbus = root->bus;
761
 
757
 
762
        dm_add_pci_bus(pbus);
758
        dm_add_pci_bus(pbus);
763
    };
759
    };
764
 
760
 
765
    dm_add_acpi(acpi_root);
761
    dm_add_acpi(acpi_root);
766
};
762
};
767
 
763
 
768
static void print_pci_resource(struct resource *res)
764
static void print_pci_resource(struct resource *res)
769
{
765
{
770
    if(res->flags !=0 )
766
    if(res->flags !=0 )
771
    {
767
    {
772
        if(res->flags & IORESOURCE_IO)
768
        if(res->flags & IORESOURCE_IO)
773
            dbgprintf("  IO range ");
769
            dbgprintf("  IO range ");
774
        else if(res->flags & IORESOURCE_MEM)
770
        else if(res->flags & IORESOURCE_MEM)
775
            dbgprintf("  MMIO range ");
771
            dbgprintf("  MMIO range ");
776
        dbgprintf("%x - %x\n", res->start, res->end);
772
        dbgprintf("%x - %x\n", res->start, res->end);
777
    };
773
    };
778
};
774
};
779
 
775
 
780
static ACPI_STATUS
776
static ACPI_STATUS
781
print_acpi_resource(ACPI_RESOURCE *acpi_res, void *data)
777
print_acpi_resource(ACPI_RESOURCE *acpi_res, void *data)
782
{
778
{
783
    ACPI_RESOURCE_ADDRESS64 addr;
779
    ACPI_RESOURCE_ADDRESS64 addr;
784
    ACPI_STATUS status;
780
    ACPI_STATUS status;
785
    int i;
781
    int i;
786
 
782
 
787
    switch (acpi_res->Type)
783
    switch (acpi_res->Type)
788
    {
784
    {
789
        case ACPI_RESOURCE_TYPE_IRQ:
785
        case ACPI_RESOURCE_TYPE_IRQ:
790
        {
786
        {
791
            ACPI_RESOURCE_IRQ *irq_data = (ACPI_RESOURCE_IRQ*)&acpi_res->Data;
787
            ACPI_RESOURCE_IRQ *irq_data = (ACPI_RESOURCE_IRQ*)&acpi_res->Data;
792
            dbgprintf(" IRQ %d\n", irq_data->Interrupts[0]);
788
            dbgprintf(" IRQ %d\n", irq_data->Interrupts[0]);
793
        };
789
        };
794
        break;
790
        break;
795
 
791
 
796
        case ACPI_RESOURCE_TYPE_EXTENDED_IRQ:
792
        case ACPI_RESOURCE_TYPE_EXTENDED_IRQ:
797
        {
793
        {
798
            ACPI_RESOURCE_EXTENDED_IRQ *irq_data = (ACPI_RESOURCE_EXTENDED_IRQ*)&acpi_res->Data;
794
            ACPI_RESOURCE_EXTENDED_IRQ *irq_data = (ACPI_RESOURCE_EXTENDED_IRQ*)&acpi_res->Data;
799
            dbgprintf(" IRQ %d\n", irq_data->Interrupts[0]);
795
            dbgprintf(" IRQ %d\n", irq_data->Interrupts[0]);
800
        };
796
        };
801
        break;
797
        break;
802
 
798
 
803
        case ACPI_RESOURCE_TYPE_DMA:
799
        case ACPI_RESOURCE_TYPE_DMA:
804
        {
800
        {
805
            ACPI_RESOURCE_DMA *dma_data = (ACPI_RESOURCE_DMA*) &acpi_res->Data;
801
            ACPI_RESOURCE_DMA *dma_data = (ACPI_RESOURCE_DMA*) &acpi_res->Data;
806
            for(i=0; i < dma_data->ChannelCount; i++)
802
            for(i=0; i < dma_data->ChannelCount; i++)
807
            {
803
            {
808
                dbgprintf(" DMA %s channel %d\n",
804
                dbgprintf(" DMA %s channel %d\n",
809
                          dma_data->Type == ACPI_TYPE_A ? "Type A":
805
                          dma_data->Type == ACPI_TYPE_A ? "Type A":
810
                          dma_data->Type == ACPI_TYPE_B ? "Type B" :
806
                          dma_data->Type == ACPI_TYPE_B ? "Type B" :
811
                          dma_data->Type == ACPI_TYPE_F ? "Type F" : "",
807
                          dma_data->Type == ACPI_TYPE_F ? "Type F" : "",
812
                          dma_data->Channels[i]);
808
                          dma_data->Channels[i]);
813
            }
809
            }
814
        };
810
        };
815
        break;
811
        break;
816
 
812
 
817
        case ACPI_RESOURCE_TYPE_IO:
813
        case ACPI_RESOURCE_TYPE_IO:
818
        {
814
        {
819
            ACPI_RESOURCE_IO *io_data = (ACPI_RESOURCE_IO*) &acpi_res->Data;
815
            ACPI_RESOURCE_IO *io_data = (ACPI_RESOURCE_IO*) &acpi_res->Data;
820
 
816
 
821
            dbgprintf(" IO range 0%x-0%x\n",io_data->Minimum,
817
            dbgprintf(" IO range 0%x-0%x\n",io_data->Minimum,
822
                       io_data->Minimum+io_data->AddressLength-1);
818
                       io_data->Minimum+io_data->AddressLength-1);
823
        }
819
        }
824
        break;
820
        break;
825
 
821
 
826
        case ACPI_RESOURCE_TYPE_FIXED_IO:
822
        case ACPI_RESOURCE_TYPE_FIXED_IO:
827
        {
823
        {
828
            ACPI_RESOURCE_FIXED_IO *io_data = (ACPI_RESOURCE_FIXED_IO*) &acpi_res->Data;
824
            ACPI_RESOURCE_FIXED_IO *io_data = (ACPI_RESOURCE_FIXED_IO*) &acpi_res->Data;
829
            dbgprintf(" Fixed IO range 0%x-0%x\n",io_data->Address,
825
            dbgprintf(" Fixed IO range 0%x-0%x\n",io_data->Address,
830
                       io_data->Address+io_data->AddressLength-1);
826
                       io_data->Address+io_data->AddressLength-1);
831
        };
827
        };
832
        break;
828
        break;
833
 
829
 
834
        case ACPI_RESOURCE_TYPE_MEMORY24:
830
        case ACPI_RESOURCE_TYPE_MEMORY24:
835
        case ACPI_RESOURCE_TYPE_MEMORY32:
831
        case ACPI_RESOURCE_TYPE_MEMORY32:
836
        case ACPI_RESOURCE_TYPE_FIXED_MEMORY32:
832
        case ACPI_RESOURCE_TYPE_FIXED_MEMORY32:
837
        {
833
        {
838
            ACPI_RESOURCE_ADDRESS64 addr64;
834
            ACPI_RESOURCE_ADDRESS64 addr64;
839
            resource_to_addr(acpi_res, &addr64);
835
            resource_to_addr(acpi_res, &addr64);
840
            dbgprintf(" Memory range 0%x-0%x\n",
836
            dbgprintf(" Memory range 0%x-0%x\n",
841
                       (uint32_t)addr64.Minimum, (uint32_t)addr64.Maximum);
837
                       (uint32_t)addr64.Minimum, (uint32_t)addr64.Maximum);
842
        }
838
        }
843
        break;
839
        break;
844
 
840
 
845
        case ACPI_RESOURCE_TYPE_ADDRESS16:
841
        case ACPI_RESOURCE_TYPE_ADDRESS16:
846
        case ACPI_RESOURCE_TYPE_ADDRESS32:
842
        case ACPI_RESOURCE_TYPE_ADDRESS32:
847
        case ACPI_RESOURCE_TYPE_ADDRESS64:
843
        case ACPI_RESOURCE_TYPE_ADDRESS64:
848
        {
844
        {
849
            ACPI_RESOURCE_ADDRESS64 addr64;
845
            ACPI_RESOURCE_ADDRESS64 addr64;
850
            ACPI_STATUS status;
846
            ACPI_STATUS status;
851
 
847
 
852
            status = AcpiResourceToAddress64(acpi_res, &addr64);
848
            status = AcpiResourceToAddress64(acpi_res, &addr64);
853
            if (ACPI_SUCCESS(status))
849
            if (ACPI_SUCCESS(status))
854
            {
850
            {
855
                dbgprintf(" Address range 0%x-0%x\n",
851
                dbgprintf(" Address range 0%x-0%x\n",
856
                       (uint32_t)addr64.Minimum, (uint32_t)addr64.Maximum);
852
                       (uint32_t)addr64.Minimum, (uint32_t)addr64.Maximum);
857
            }
853
            }
858
        };
854
        };
859
        break;
855
        break;
860
    };
856
    };
861
 
857
 
862
    return AE_OK;
858
    return AE_OK;
863
};
859
};
864
 
860
 
865
 
861
 
866
static void print_dm_list()
862
static void print_dm_list()
867
{
863
{
868
    struct pci_dev     *pcidev;
864
    struct pci_dev     *pcidev;
869
    struct acpi_device *acpidev;
865
    struct acpi_device *acpidev;
870
    dmdev_t  *dmdev;
866
    dmdev_t  *dmdev;
871
    uint32_t  i;
867
    uint32_t  i;
872
 
868
 
873
    dbgprintf("\nDevices:\n");
869
    dbgprintf("\nDevices:\n");
874
 
870
 
875
    list_for_each_entry(dmdev, &dmdev_tree, list)
871
    list_for_each_entry(dmdev, &dmdev_tree, list)
876
    {
872
    {
877
        switch(dmdev->type)
873
        switch(dmdev->type)
878
        {
874
        {
879
            case 0:
875
            case 0:
880
               if(dmdev->acpi_dev != NULL)
876
               if(dmdev->acpi_dev != NULL)
881
               {
877
               {
882
                    acpidev = dmdev->acpi_dev;
878
                    acpidev = dmdev->acpi_dev;
883
                    dbgprintf("\n%s\n", acpidev->pnp.bus_id);
879
                    dbgprintf("\n%s\n", acpidev->pnp.bus_id);
884
                    AcpiWalkResources(acpidev->handle, METHOD_NAME__CRS,
880
                    AcpiWalkResources(acpidev->handle, METHOD_NAME__CRS,
885
                                      print_acpi_resource, NULL);
881
                                      print_acpi_resource, NULL);
886
               };
882
               };
887
               break;
883
               break;
888
 
884
 
889
            case 1:
885
            case 1:
890
               if(dmdev->pci_dev != NULL)
886
               if(dmdev->pci_dev != NULL)
891
               {
887
               {
892
                   pcidev = dmdev->pci_dev;
888
                   pcidev = dmdev->pci_dev;
893
                   dbgprintf("\nPCI_%x_%x bus:%d devfn: %x\n",
889
                   dbgprintf("\nPCI_%x_%x bus:%d devfn: %x\n",
894
                               pcidev->vendor, pcidev->device,
890
                               pcidev->vendor, pcidev->device,
895
                               pcidev->busnr, pcidev->devfn);
891
                               pcidev->busnr, pcidev->devfn);
896
 
892
 
897
                   for(i = 0; i < DEVICE_COUNT_RESOURCE; i++)
893
                   for(i = 0; i < DEVICE_COUNT_RESOURCE; i++)
898
                       print_pci_resource(&pcidev->resource[i]);
894
                       print_pci_resource(&pcidev->resource[i]);
899
 
895
 
900
                   if(pcidev->pin)
896
                   if(pcidev->pin)
901
                       dbgprintf("  APIC IRQ: %d\n", acpi_get_irq(pcidev));
897
                       dbgprintf("  APIC IRQ: %d\n", acpi_get_irq(pcidev));
902
               };
898
               };
903
               break;
899
               break;
904
        };
900
        };
905
    };
901
    };
906
};
902
};
907
 
903
 
908
 
904
 
909
typedef struct
905
typedef struct
910
{
906
{
911
    uint32_t  busaddr;
907
    uint32_t  busaddr;
912
    uint32_t  devid;
908
    uint32_t  devid;
913
    uint32_t  irq;
909
    uint32_t  irq;
914
    uint32_t  unused;
910
    uint32_t  unused;
915
}devinfo_t;
911
}devinfo_t;
916
 
912
 
917
#pragma pack(push, 1)
913
#pragma pack(push, 1)
918
typedef struct
914
typedef struct
919
{
915
{
920
  char sec;
916
  char sec;
921
  char min;
917
  char min;
922
  char hour;
918
  char hour;
923
  char rsv;
919
  char rsv;
924
}detime_t;
920
}detime_t;
925
 
921
 
926
typedef struct
922
typedef struct
927
{
923
{
928
  char  day;
924
  char  day;
929
  char  month;
925
  char  month;
930
  short year;
926
  short year;
931
}dedate_t;
927
}dedate_t;
932
 
928
 
933
typedef struct
929
typedef struct
934
{
930
{
935
  unsigned    attr;
931
  unsigned    attr;
936
  unsigned    flags;
932
  unsigned    flags;
937
  union
933
  union
938
  {
934
  {
939
     detime_t  ctime;
935
     detime_t  ctime;
940
     unsigned  cr_time;
936
     unsigned  cr_time;
941
  };
937
  };
942
  union
938
  union
943
  {
939
  {
944
     dedate_t  cdate;
940
     dedate_t  cdate;
945
     unsigned  cr_date;
941
     unsigned  cr_date;
946
  };
942
  };
947
  union
943
  union
948
  {
944
  {
949
     detime_t  atime;
945
     detime_t  atime;
950
     unsigned  acc_time;
946
     unsigned  acc_time;
951
  };
947
  };
952
  union
948
  union
953
  {
949
  {
954
     dedate_t  adate;
950
     dedate_t  adate;
955
     unsigned  acc_date;
951
     unsigned  acc_date;
956
  };
952
  };
957
  union
953
  union
958
  {
954
  {
959
     detime_t  mtime;
955
     detime_t  mtime;
960
     unsigned  mod_time;
956
     unsigned  mod_time;
961
  };
957
  };
962
  union
958
  union
963
  {
959
  {
964
     dedate_t  mdate;
960
     dedate_t  mdate;
965
     unsigned  mod_date;
961
     unsigned  mod_date;
966
  };
962
  };
967
  unsigned    size;
963
  unsigned    size;
968
  unsigned    size_high;
964
  unsigned    size_high;
969
} FILEINFO;
965
} FILEINFO;
970
 
966
 
971
#pragma pack(pop)
967
#pragma pack(pop)
972
 
968
 
973
 
969
 
974
int write_device_dat(char *path)
970
int write_device_dat(char *path)
975
{
971
{
976
    struct pci_dev   *pcidev;
972
    struct pci_dev   *pcidev;
977
    dmdev_t          *dmdev;
973
    dmdev_t          *dmdev;
978
    devinfo_t        *data;
974
    devinfo_t        *data;
979
    int               writes;
975
    int               writes;
980
    int               len;
976
    int               len;
981
    int i = 0;
977
    int i = 0;
982
 
978
 
983
    list_for_each_entry(dmdev, &dmdev_tree, list)
979
    list_for_each_entry(dmdev, &dmdev_tree, list)
984
    {
980
    {
985
        if(dmdev->type ==1)
981
        if(dmdev->type ==1)
986
        {
982
        {
987
            if(dmdev->pci_dev != NULL)
983
            if(dmdev->pci_dev != NULL)
988
            {
984
            {
989
                pcidev = dmdev->pci_dev;
985
                pcidev = dmdev->pci_dev;
990
                if(pcidev->pin)
986
                if(pcidev->pin)
991
                    i++;
987
                    i++;
992
            };
988
            };
993
        };
989
        };
994
    };
990
    };
995
 
991
 
996
    len = sizeof(devinfo_t)*i + 4;
992
    len = sizeof(devinfo_t)*i + 4;
997
    data = (devinfo_t*)malloc(len);
993
    data = (devinfo_t*)malloc(len);
998
 
994
 
999
    i = 0;
995
    i = 0;
1000
 
996
 
1001
    list_for_each_entry(dmdev, &dmdev_tree, list)
997
    list_for_each_entry(dmdev, &dmdev_tree, list)
1002
    {
998
    {
1003
        if(dmdev->type == 1)
999
        if(dmdev->type == 1)
1004
        {
1000
        {
1005
 
1001
 
1006
            if(dmdev->pci_dev != NULL)
1002
            if(dmdev->pci_dev != NULL)
1007
            {
1003
            {
1008
                pcidev = dmdev->pci_dev;
1004
                pcidev = dmdev->pci_dev;
1009
                if(pcidev->pin && (acpi_get_irq(pcidev) != -1) )
1005
                if(pcidev->pin && (acpi_get_irq(pcidev) != -1) )
1010
                {
1006
                {
1011
                    data[i].busaddr = (pcidev->busnr<<8)|pcidev->devfn;
1007
                    data[i].busaddr = (pcidev->busnr<<8)|pcidev->devfn;
1012
                    data[i].devid   = ((uint32_t)pcidev->device<<16) |
1008
                    data[i].devid   = ((uint32_t)pcidev->device<<16) |
1013
                                       pcidev->vendor;
1009
                                       pcidev->vendor;
1014
                    data[i].irq     =  acpi_get_irq(pcidev);
1010
                    data[i].irq     =  acpi_get_irq(pcidev);
1015
                    data[i].unused  =  0;
1011
                    data[i].unused  =  0;
1016
                    i++;
1012
                    i++;
1017
                }
1013
                }
1018
            };
1014
            };
1019
        };
1015
        };
1020
    };
1016
    };
1021
 
1017
 
1022
    data[i].busaddr = -1;
1018
    data[i].busaddr = -1;
1023
 
1019
 
1024
    FILEINFO info;
1020
    FILEINFO info;
1025
 
1021
 
1026
    int offset = 0;
1022
    int offset = 0;
1027
 
1023
 
1028
    if(get_fileinfo(path,&info))
1024
    if(get_fileinfo(path,&info))
1029
    {
1025
    {
1030
        if( create_file(path))
1026
        if( create_file(path))
1031
        {
1027
        {
1032
            free(data);
1028
            free(data);
1033
            return false;
1029
            return false;
1034
        }
1030
        }
1035
    }
1031
    }
1036
    else
1032
    else
1037
        set_file_size(path, 0);
1033
        set_file_size(path, 0);
1038
 
1034
 
1039
    write_file(path, data, 0, len, &writes);
1035
    write_file(path, data, 0, len, &writes);
1040
 
1036
 
1041
    return true;
1037
    return true;
1042
};
1038
};