bzr branch
http://suren.me/webbzr/alps/pcitool
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
1 |
#include <stdio.h> |
2 |
#include <string.h> |
|
3 |
#include <strings.h> |
|
4 |
#include <stdlib.h> |
|
5 |
#include <stdint.h> |
|
6 |
#include <stdarg.h> |
|
7 |
#include <fcntl.h> |
|
8 |
#include <unistd.h> |
|
9 |
#include <sys/ioctl.h> |
|
10 |
#include <sys/mman.h> |
|
11 |
#include <arpa/inet.h> |
|
12 |
#include <errno.h> |
|
13 |
#include <assert.h> |
|
14 |
||
15 |
#include "pci.h" |
|
16 |
||
17 |
#include "tools.h" |
|
18 |
#include "error.h" |
|
19 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
20 |
int pcilib_add_registers(pcilib_t *ctx, size_t n, pcilib_register_description_t *registers) { |
21 |
pcilib_register_description_t *regs; |
|
22 |
size_t size, n_present, n_new; |
|
23 |
||
24 |
if (!n) { |
|
25 |
for (n = 0; registers[n].bits; n++); |
|
26 |
}
|
|
27 |
||
28 |
||
55
by Suren A. Chilingaryan
IRQ support in NWL DMA engine |
29 |
if (pcilib_model[ctx->model].registers) |
30 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
31 |
if (ctx->model_info.registers == pcilib_model[ctx->model].registers) { |
32 |
for (n_present = 0; ctx->model_info.registers[n_present].bits; n_present++); |
|
33 |
for (size = 1024; size < 2 * (n + n_present + 1); size<<=1); |
|
34 |
regs = (pcilib_register_description_t*)malloc(size * sizeof(pcilib_register_description_t)); |
|
35 |
if (!regs) return PCILIB_ERROR_MEMORY; |
|
36 |
||
37 |
ctx->model_info.registers = regs; |
|
38 |
ctx->num_reg = n + n_present; |
|
39 |
ctx->alloc_reg = size; |
|
40 |
||
41 |
memcpy(ctx->model_info.registers, pcilib_model[ctx->model].registers, (n_present + 1) * sizeof(pcilib_register_description_t)); |
|
42 |
} else { |
|
43 |
n_present = ctx->num_reg; |
|
44 |
if ((n_present + n + 1) > ctx->alloc_reg) { |
|
45 |
for (size = ctx->alloc_reg; size < 2 * (n + n_present + 1); size<<=1); |
|
46 |
||
47 |
regs = (pcilib_register_description_t*)realloc(ctx->model_info.registers, size * sizeof(pcilib_register_description_t)); |
|
48 |
if (!regs) return PCILIB_ERROR_MEMORY; |
|
49 |
||
50 |
ctx->model_info.registers = regs; |
|
51 |
ctx->alloc_reg = size; |
|
52 |
}
|
|
53 |
ctx->num_reg += n; |
|
54 |
}
|
|
55 |
||
56 |
memcpy(ctx->model_info.registers + ctx->num_reg, ctx->model_info.registers + n_present, sizeof(pcilib_register_description_t)); |
|
57 |
memcpy(ctx->model_info.registers + n_present, registers, n * sizeof(pcilib_register_description_t)); |
|
58 |
||
59 |
return 0; |
|
60 |
}
|
|
61 |
||
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
62 |
pcilib_register_bank_t pcilib_find_bank_by_addr(pcilib_t *ctx, pcilib_register_bank_addr_t bank) { |
63 |
pcilib_register_bank_t i; |
|
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
64 |
pcilib_model_description_t *model_info = pcilib_get_model_description(ctx); |
65 |
pcilib_register_bank_description_t *banks = model_info->banks; |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
66 |
|
67 |
for (i = 0; banks[i].access; i++) |
|
68 |
if (banks[i].addr == bank) return i; |
|
69 |
||
70 |
return -1; |
|
71 |
}
|
|
72 |
||
73 |
pcilib_register_bank_t pcilib_find_bank_by_name(pcilib_t *ctx, const char *bankname) { |
|
74 |
pcilib_register_bank_t i; |
|
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
75 |
pcilib_model_description_t *model_info = pcilib_get_model_description(ctx); |
76 |
pcilib_register_bank_description_t *banks = model_info->banks; |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
77 |
|
78 |
for (i = 0; banks[i].access; i++) |
|
79 |
if (!strcasecmp(banks[i].name, bankname)) return i; |
|
80 |
||
81 |
return -1; |
|
82 |
}
|
|
83 |
||
84 |
pcilib_register_bank_t pcilib_find_bank(pcilib_t *ctx, const char *bank) { |
|
85 |
pcilib_register_bank_t res; |
|
86 |
unsigned long addr; |
|
87 |
||
88 |
if (!bank) { |
|
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
89 |
pcilib_model_description_t *model_info = pcilib_get_model_description(ctx); |
90 |
pcilib_register_bank_description_t *banks = model_info->banks; |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
91 |
if ((banks)&&(banks[0].access)) return (pcilib_register_bank_t)0; |
92 |
return -1; |
|
93 |
}
|
|
94 |
||
95 |
if (pcilib_isxnumber(bank)&&(sscanf(bank,"%lx", &addr) == 1)) { |
|
96 |
res = pcilib_find_bank_by_addr(ctx, addr); |
|
97 |
if (res != PCILIB_REGISTER_BANK_INVALID) return res; |
|
98 |
}
|
|
99 |
||
100 |
return pcilib_find_bank_by_name(ctx, bank); |
|
101 |
}
|
|
102 |
||
103 |
// FIXME create hash during map_register space
|
|
104 |
pcilib_register_t pcilib_find_register(pcilib_t *ctx, const char *bank, const char *reg) { |
|
105 |
pcilib_register_t i; |
|
106 |
pcilib_register_bank_t bank_id; |
|
107 |
pcilib_register_bank_addr_t bank_addr; |
|
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
108 |
|
109 |
pcilib_model_description_t *model_info = pcilib_get_model_description(ctx); |
|
110 |
pcilib_register_description_t *registers = model_info->registers; |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
111 |
|
112 |
if (bank) { |
|
113 |
bank_id = pcilib_find_bank(ctx, bank); |
|
114 |
if (bank_id == PCILIB_REGISTER_BANK_INVALID) { |
|
115 |
pcilib_error("Invalid bank (%s) is specified", bank); |
|
116 |
return -1; |
|
117 |
}
|
|
118 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
119 |
bank_addr = model_info->banks[bank_id].addr; |
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
120 |
}
|
121 |
||
122 |
for (i = 0; registers[i].bits; i++) { |
|
123 |
if ((!strcasecmp(registers[i].name, reg))&&((!bank)||(registers[i].bank == bank_addr))) return i; |
|
124 |
}
|
|
125 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
126 |
if ((ctx->model_info.dma_api)&&(!ctx->dma_ctx)&&(pcilib_get_dma_info(ctx))) { |
127 |
registers = model_info->registers; |
|
128 |
||
129 |
for (; registers[i].bits; i++) { |
|
130 |
if ((!strcasecmp(registers[i].name, reg))&&((!bank)||(registers[i].bank == bank_addr))) return i; |
|
131 |
}
|
|
132 |
}
|
|
133 |
||
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
134 |
return (pcilib_register_t)-1; |
135 |
};
|
|
136 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
137 |
static int pcilib_read_register_space_internal(pcilib_t *ctx, pcilib_register_bank_t bank, pcilib_register_addr_t addr, size_t n, pcilib_register_size_t offset, pcilib_register_size_t bits, pcilib_register_value_t *buf) { |
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
138 |
int err; |
139 |
int rest; |
|
140 |
size_t i; |
|
141 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
142 |
pcilib_model_description_t *model_info = pcilib_get_model_description(ctx); |
143 |
pcilib_register_bank_description_t *b = model_info->banks + bank; |
|
116
by Suren A. Chilingaryan
Fix multiword register reads in a proper way |
144 |
|
145 |
int access = b->access / 8; |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
146 |
|
147 |
assert(bits < 8 * sizeof(pcilib_register_value_t)); |
|
148 |
||
149 |
if (((addr + n) > b->size)||(((addr + n) == b->size)&&(bits))) { |
|
102
by Suren A. Chilingaryan
Accept short addresses for IPECamera FPGA registers |
150 |
if ((b->format)&&(strchr(b->format, 'x'))) |
151 |
pcilib_error("Accessing register (%u regs at addr 0x%x) out of register space (%u registers total)", bits?(n+1):n, addr, b->size); |
|
152 |
else
|
|
153 |
pcilib_error("Accessing register (%u regs at addr %u) out of register space (%u registers total)", bits?(n+1):n, addr, b->size); |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
154 |
return PCILIB_ERROR_OUTOFRANGE; |
155 |
}
|
|
156 |
||
157 |
err = pcilib_map_register_space(ctx); |
|
158 |
if (err) { |
|
159 |
pcilib_error("Failed to map the register space"); |
|
160 |
return err; |
|
161 |
}
|
|
162 |
||
163 |
//n += bits / b->access;
|
|
164 |
//bits %= b->access;
|
|
165 |
||
166 |
for (i = 0; i < n; i++) { |
|
116
by Suren A. Chilingaryan
Fix multiword register reads in a proper way |
167 |
err = pcilib_protocol[b->protocol].read(ctx, b, addr + i * access, buf + i); |
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
168 |
if (err) break; |
169 |
}
|
|
170 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
171 |
if ((bits > 0)&&(!err)) { |
172 |
pcilib_register_value_t val = 0; |
|
116
by Suren A. Chilingaryan
Fix multiword register reads in a proper way |
173 |
err = pcilib_protocol[b->protocol].read(ctx, b, addr + n * access, &val); |
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
174 |
|
175 |
val = (val >> offset)&BIT_MASK(bits); |
|
176 |
memcpy(buf + n, &val, sizeof(pcilib_register_value_t)); |
|
177 |
}
|
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
178 |
|
179 |
return err; |
|
180 |
}
|
|
181 |
||
182 |
int pcilib_read_register_space(pcilib_t *ctx, const char *bank, pcilib_register_addr_t addr, size_t n, pcilib_register_value_t *buf) { |
|
183 |
pcilib_register_bank_t bank_id = pcilib_find_bank(ctx, bank); |
|
184 |
if (bank_id == PCILIB_REGISTER_BANK_INVALID) { |
|
185 |
if (bank) pcilib_error("Invalid register bank is specified (%s)", bank); |
|
186 |
else pcilib_error("Register bank should be specified"); |
|
187 |
return PCILIB_ERROR_INVALID_BANK; |
|
188 |
}
|
|
189 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
190 |
return pcilib_read_register_space_internal(ctx, bank_id, addr, n, 0, 0, buf); |
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
191 |
}
|
192 |
||
193 |
int pcilib_read_register_by_id(pcilib_t *ctx, pcilib_register_t reg, pcilib_register_value_t *value) { |
|
194 |
int err; |
|
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
195 |
size_t i, n; |
196 |
pcilib_register_size_t bits; |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
197 |
pcilib_register_value_t res; |
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
198 |
pcilib_register_bank_t bank; |
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
199 |
pcilib_register_description_t *r; |
200 |
pcilib_register_bank_description_t *b; |
|
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
201 |
pcilib_model_description_t *model_info = pcilib_get_model_description(ctx); |
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
202 |
|
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
203 |
r = model_info->registers + reg; |
204 |
||
205 |
bank = pcilib_find_bank_by_addr(ctx, r->bank); |
|
206 |
if (bank == PCILIB_REGISTER_BANK_INVALID) return PCILIB_ERROR_INVALID_BANK; |
|
207 |
||
208 |
b = model_info->banks + bank; |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
209 |
|
210 |
n = r->bits / b->access; |
|
211 |
bits = r->bits % b->access; |
|
212 |
||
213 |
pcilib_register_value_t buf[n + 1]; |
|
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
214 |
err = pcilib_read_register_space_internal(ctx, bank, r->addr, n, r->offset, bits, buf); |
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
215 |
|
216 |
if ((b->endianess == PCILIB_BIG_ENDIAN)||((b->endianess == PCILIB_HOST_ENDIAN)&&(ntohs(1) == 1))) { |
|
217 |
pcilib_error("Big-endian byte order support is not implemented"); |
|
218 |
return PCILIB_ERROR_NOTSUPPORTED; |
|
219 |
} else { |
|
220 |
res = 0; |
|
221 |
if (bits) ++n; |
|
222 |
for (i = 0; i < n; i++) { |
|
223 |
res |= buf[i] << (i * b->access); |
|
224 |
}
|
|
225 |
}
|
|
226 |
||
227 |
*value = res; |
|
228 |
||
229 |
return err; |
|
230 |
}
|
|
231 |
||
232 |
||
233 |
int pcilib_read_register(pcilib_t *ctx, const char *bank, const char *regname, pcilib_register_value_t *value) { |
|
234 |
int err; |
|
235 |
int reg; |
|
236 |
||
237 |
reg = pcilib_find_register(ctx, bank, regname); |
|
238 |
if (reg < 0) { |
|
239 |
pcilib_error("Register (%s) is not found", regname); |
|
240 |
return PCILIB_ERROR_NOTFOUND; |
|
241 |
}
|
|
242 |
||
243 |
return pcilib_read_register_by_id(ctx, reg, value); |
|
244 |
}
|
|
245 |
||
246 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
247 |
static int pcilib_write_register_space_internal(pcilib_t *ctx, pcilib_register_bank_t bank, pcilib_register_addr_t addr, size_t n, pcilib_register_size_t offset, pcilib_register_size_t bits, pcilib_register_value_t rwmask, pcilib_register_value_t *buf) { |
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
248 |
int err; |
249 |
int rest; |
|
250 |
size_t i; |
|
251 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
252 |
pcilib_model_description_t *model_info = pcilib_get_model_description(ctx); |
253 |
pcilib_register_bank_description_t *b = model_info->banks + bank; |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
254 |
|
116
by Suren A. Chilingaryan
Fix multiword register reads in a proper way |
255 |
int access = b->access / 8; |
256 |
||
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
257 |
assert(bits < 8 * sizeof(pcilib_register_value_t)); |
258 |
||
259 |
if (((addr + n) > b->size)||(((addr + n) == b->size)&&(bits))) { |
|
102
by Suren A. Chilingaryan
Accept short addresses for IPECamera FPGA registers |
260 |
if ((b->format)&&(strchr(b->format, 'x'))) |
261 |
pcilib_error("Accessing register (%u regs at addr 0x%x) out of register space (%u registers total)", bits?(n+1):n, addr, b->size); |
|
262 |
else
|
|
263 |
pcilib_error("Accessing register (%u regs at addr %u) out of register space (%u registers total)", bits?(n+1):n, addr, b->size); |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
264 |
return PCILIB_ERROR_OUTOFRANGE; |
265 |
}
|
|
266 |
||
267 |
err = pcilib_map_register_space(ctx); |
|
268 |
if (err) { |
|
269 |
pcilib_error("Failed to map the register space"); |
|
270 |
return err; |
|
271 |
}
|
|
272 |
||
273 |
//n += bits / b->access;
|
|
274 |
//bits %= b->access;
|
|
275 |
||
276 |
for (i = 0; i < n; i++) { |
|
116
by Suren A. Chilingaryan
Fix multiword register reads in a proper way |
277 |
err = pcilib_protocol[b->protocol].write(ctx, b, addr + i * access, buf[i]); |
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
278 |
if (err) break; |
279 |
}
|
|
280 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
281 |
if ((bits > 0)&&(!err)) { |
282 |
pcilib_register_value_t val = (buf[n]&BIT_MASK(bits))<<offset; |
|
283 |
pcilib_register_value_t mask = BIT_MASK(bits)<<offset; |
|
284 |
||
285 |
if (~mask&rwmask) { |
|
286 |
pcilib_register_value_t rval; |
|
287 |
||
116
by Suren A. Chilingaryan
Fix multiword register reads in a proper way |
288 |
err = pcilib_protocol[b->protocol].read(ctx, b, addr + n * access, &rval); |
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
289 |
if (err) return err; |
290 |
||
291 |
val |= (rval & rwmask & ~mask); |
|
292 |
}
|
|
293 |
||
116
by Suren A. Chilingaryan
Fix multiword register reads in a proper way |
294 |
err = pcilib_protocol[b->protocol].write(ctx, b, addr + n * access, val); |
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
295 |
}
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
296 |
|
297 |
return err; |
|
298 |
}
|
|
299 |
||
300 |
int pcilib_write_register_space(pcilib_t *ctx, const char *bank, pcilib_register_addr_t addr, size_t n, pcilib_register_value_t *buf) { |
|
301 |
pcilib_register_bank_t bank_id = pcilib_find_bank(ctx, bank); |
|
302 |
if (bank_id == PCILIB_REGISTER_BANK_INVALID) { |
|
303 |
if (bank) pcilib_error("Invalid register bank is specified (%s)", bank); |
|
304 |
else pcilib_error("Register bank should be specified"); |
|
305 |
return PCILIB_ERROR_INVALID_BANK; |
|
306 |
}
|
|
307 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
308 |
return pcilib_write_register_space_internal(ctx, bank_id, addr, n, 0, 0, 0, buf); |
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
309 |
}
|
310 |
||
311 |
||
312 |
int pcilib_write_register_by_id(pcilib_t *ctx, pcilib_register_t reg, pcilib_register_value_t value) { |
|
313 |
int err; |
|
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
314 |
size_t i, n; |
315 |
pcilib_register_size_t bits; |
|
316 |
pcilib_register_bank_t bank; |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
317 |
pcilib_register_value_t res; |
318 |
pcilib_register_description_t *r; |
|
319 |
pcilib_register_bank_description_t *b; |
|
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
320 |
pcilib_model_description_t *model_info = pcilib_get_model_description(ctx); |
321 |
||
322 |
r = model_info->registers + reg; |
|
323 |
||
324 |
bank = pcilib_find_bank_by_addr(ctx, r->bank); |
|
325 |
if (bank == PCILIB_REGISTER_BANK_INVALID) return PCILIB_ERROR_INVALID_BANK; |
|
326 |
||
327 |
b = model_info->banks + bank; |
|
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
328 |
|
329 |
n = r->bits / b->access; |
|
330 |
bits = r->bits % b->access; |
|
331 |
||
332 |
pcilib_register_value_t buf[n + 1]; |
|
333 |
memset(buf, 0, (n + 1) * sizeof(pcilib_register_value_t)); |
|
334 |
||
335 |
if ((b->endianess == PCILIB_BIG_ENDIAN)||((b->endianess == PCILIB_HOST_ENDIAN)&&(ntohs(1) == 1))) { |
|
336 |
pcilib_error("Big-endian byte order support is not implemented"); |
|
337 |
return PCILIB_ERROR_NOTSUPPORTED; |
|
338 |
} else { |
|
339 |
if (b->access == sizeof(pcilib_register_value_t) * 8) { |
|
340 |
buf[0] = value; |
|
341 |
} else { |
|
342 |
for (i = 0, res = value; (res > 0)&&(i <= n); ++i) { |
|
343 |
buf[i] = res & BIT_MASK(b->access); |
|
344 |
res >>= b->access; |
|
345 |
}
|
|
346 |
||
347 |
if (res) { |
|
348 |
pcilib_error("Value %i is too big to fit in the register %s", value, r->name); |
|
349 |
return PCILIB_ERROR_OUTOFRANGE; |
|
350 |
}
|
|
351 |
}
|
|
352 |
}
|
|
353 |
||
54
by Suren A. Chilingaryan
Support dynamic registers, support register offsets and multiregisters (bitmasks), list NWL DMA registers |
354 |
err = pcilib_write_register_space_internal(ctx, bank, r->addr, n, r->offset, bits, r->rwmask, buf); |
47
by Suren A. Chilingaryan
Support FIFO reading/writting, code restructurization, few fixes |
355 |
return err; |
356 |
}
|
|
357 |
||
358 |
int pcilib_write_register(pcilib_t *ctx, const char *bank, const char *regname, pcilib_register_value_t value) { |
|
359 |
int err; |
|
360 |
int reg; |
|
361 |
||
362 |
reg = pcilib_find_register(ctx, bank, regname); |
|
363 |
if (reg < 0) { |
|
364 |
pcilib_error("Register (%s) is not found", regname); |
|
365 |
return PCILIB_ERROR_NOTFOUND; |
|
366 |
}
|
|
367 |
||
368 |
return pcilib_write_register_by_id(ctx, reg, value); |
|
369 |
}
|