1/* 2 * IEEE 1394 for Linux 3 * 4 * Transaction support. 5 * 6 * Copyright (C) 1999 Andreas E. Bombe 7 * 8 * This code is licensed under the GPL. See the file COPYING in the root 9 * directory of the kernel sources for details. 10 */ 11 12#include <linux/sched.h> 13#include <asm/errno.h> 14#include <asm/bitops.h> 15 16#include "ieee1394.h" 17#include "ieee1394_types.h" 18#include "hosts.h" 19#include "ieee1394_core.h" 20#include "highlevel.h" 21 22 23#define PREP_ASYNC_HEAD_ADDRESS(tc) \ 24 packet->tcode = tc; \ 25 packet->header[0] = (packet->node_id << 16) | (packet->tlabel << 10) \ 26 | (1 << 8) | (tc << 4); \ 27 packet->header[1] = (packet->host->node_id << 16) | (addr >> 32); \ 28 packet->header[2] = addr & 0xffffffff 29 30#define PREP_ASYNC_HEAD_RCODE(tc) \ 31 packet->tcode = tc; \ 32 packet->header[0] = (packet->node_id << 16) | (packet->tlabel << 10) \ 33 | (1 << 8) | (tc << 4); \ 34 packet->header[1] = (packet->host->node_id << 16) | (rcode << 12); \ 35 packet->header[2] = 0 36 37 38void fill_async_readquad(struct hpsb_packet *packet, u64 addr) 39{ 40 PREP_ASYNC_HEAD_ADDRESS(TCODE_READQ); 41 packet->header_size = 12; 42 packet->data_size = 0; 43 packet->expect_response = 1; 44} 45 46void fill_async_readquad_resp(struct hpsb_packet *packet, int rcode, 47 quadlet_t data) 48{ 49 PREP_ASYNC_HEAD_RCODE(TCODE_READQ_RESPONSE); 50 packet->header[3] = data; 51 packet->header_size = 16; 52 packet->data_size = 0; 53} 54 55void fill_async_readblock(struct hpsb_packet *packet, u64 addr, int length) 56{ 57 PREP_ASYNC_HEAD_ADDRESS(TCODE_READB); 58 packet->header[3] = length << 16; 59 packet->header_size = 16; 60 packet->data_size = 0; 61 packet->expect_response = 1; 62} 63 64void fill_async_readblock_resp(struct hpsb_packet *packet, int rcode, 65 int length) 66{ 67 if (rcode != RCODE_COMPLETE) { 68 length = 0; 69 } 70 71 PREP_ASYNC_HEAD_RCODE(TCODE_READB_RESPONSE); 72 packet->header[3] = length << 16; 73 packet->header_size = 16; 74 packet->data_size = length + (length % 4 ? 4 - (length % 4) : 0); 75} 76 77void fill_async_writequad(struct hpsb_packet *packet, u64 addr, quadlet_t data) 78{ 79 PREP_ASYNC_HEAD_ADDRESS(TCODE_WRITEQ); 80 packet->header[3] = data; 81 packet->header_size = 16; 82 packet->data_size = 0; 83 packet->expect_response = 1; 84} 85 86void fill_async_writeblock(struct hpsb_packet *packet, u64 addr, int length) 87{ 88 PREP_ASYNC_HEAD_ADDRESS(TCODE_WRITEB); 89 packet->header[3] = length << 16; 90 packet->header_size = 16; 91 packet->expect_response = 1; 92 packet->data_size = length + (length % 4 ? 4 - (length % 4) : 0); 93} 94 95void fill_async_write_resp(struct hpsb_packet *packet, int rcode) 96{ 97 PREP_ASYNC_HEAD_RCODE(TCODE_WRITE_RESPONSE); 98 packet->header[2] = 0; 99 packet->header_size = 12; 100 packet->data_size = 0; 101} 102 103void fill_async_lock(struct hpsb_packet *packet, u64 addr, int extcode, 104 int length) 105{ 106 PREP_ASYNC_HEAD_ADDRESS(TCODE_LOCK_REQUEST); 107 packet->header[3] = (length << 16) | extcode; 108 packet->header_size = 16; 109 packet->data_size = length; 110 packet->expect_response = 1; 111} 112 113void fill_async_lock_resp(struct hpsb_packet *packet, int rcode, int extcode, 114 int length) 115{ 116 if (rcode != RCODE_COMPLETE) { 117 length = 0; 118 } 119 120 PREP_ASYNC_HEAD_RCODE(TCODE_LOCK_RESPONSE); 121 packet->header[3] = (length << 16) | extcode; 122 packet->header_size = 16; 123 packet->data_size = length; 124} 125 126void fill_iso_packet(struct hpsb_packet *packet, int length, int channel, 127 int tag, int sync) 128{ 129 packet->header[0] = (length << 16) | (tag << 14) | (channel << 8) 130 | (TCODE_ISO_DATA << 4) | sync; 131 132 packet->header_size = 4; 133 packet->data_size = length; 134 packet->type = hpsb_iso; 135 packet->tcode = TCODE_ISO_DATA; 136} 137 138void fill_phy_packet(struct hpsb_packet *packet, quadlet_t data) 139{ 140 packet->header[0] = data; 141 packet->header[1] = ~data; 142 packet->header_size = 8; 143 packet->data_size = 0; 144 packet->expect_response = 0; 145 packet->type = hpsb_raw; /* No CRC added */ 146 packet->speed_code = SPEED_100; /* Force speed to be 100Mbps */ 147} 148 149 150/** 151 * get_tlabel - allocate a transaction label 152 * @host: host to be used for transmission 153 * @nodeid: the node ID of the transmission target 154 * @wait: whether to sleep if no tlabel is available 155 * 156 * Every asynchronous transaction on the 1394 bus needs a transaction label to 157 * match the response to the request. This label has to be different from any 158 * other transaction label in an outstanding request to the same node to make 159 * matching possible without ambiguity. 160 * 161 * There are 64 different tlabels, so an allocated tlabel has to be freed with 162 * free_tlabel() after the transaction is complete (unless it's reused again for 163 * the same target node). 164 * 165 * @wait must not be set to true if you are calling from interrupt context. 166 * 167 * Return value: The allocated transaction label or -1 if there was no free 168 * tlabel and @wait is false. 169 */ 170int get_tlabel(struct hpsb_host *host, nodeid_t nodeid, int wait) 171{ 172 int tlabel = 0; 173 unsigned long flags; 174 int found_tlabel = 0; 175 176 if (wait) { 177 down(&host->tlabel_count); 178 } else { 179 if (down_trylock(&host->tlabel_count)) return -1; 180 } 181 182 spin_lock_irqsave(&host->tlabel_lock, flags); 183 184 while (!found_tlabel) { 185 tlabel = host->tlabel_current; 186 if (tlabel < 32 && !(host->tlabel_pool[0] & 1 << tlabel)) { 187 host->tlabel_pool[0] |= 1 << tlabel; 188 found_tlabel = 1; 189 } else if (!(host->tlabel_pool[1] & 1 << (tlabel - 32))) { 190 host->tlabel_pool[1] |= 1 << (tlabel - 32); 191 found_tlabel = 1; 192 } 193 host->tlabel_current = (host->tlabel_current + 1) % 64; 194 } 195 196 spin_unlock_irqrestore(&host->tlabel_lock, flags); 197 198 return tlabel; 199} 200 201/** 202 * free_tlabel - free an allocated transaction label 203 * @host: host to be used for transmission 204 * @nodeid: the node ID of the transmission target 205 * @tlabel: the transaction label to free 206 * 207 * Frees the transaction label allocated with get_tlabel(). The tlabel has to 208 * be freed after the transaction is complete (i.e. response was received for a 209 * split transaction or packet was sent for a unified transaction). 210 * 211 * A tlabel must not be freed twice. 212 */ 213void free_tlabel(struct hpsb_host *host, nodeid_t nodeid, int tlabel) 214{ 215 unsigned long flags; 216 217 spin_lock_irqsave(&host->tlabel_lock, flags); 218 219 if (tlabel < 32) { 220 host->tlabel_pool[0] &= ~(1 << tlabel); 221 } else { 222 host->tlabel_pool[1] &= ~(1 << (tlabel-32)); 223 } 224 225 spin_unlock_irqrestore(&host->tlabel_lock, flags); 226 227 up(&host->tlabel_count); 228} 229 230 231 232int hpsb_packet_success(struct hpsb_packet *packet) 233{ 234 switch (packet->ack_code) { 235 case ACK_PENDING: 236 switch ((packet->header[1] >> 12) & 0xf) { 237 case RCODE_COMPLETE: 238 return 0; 239 case RCODE_CONFLICT_ERROR: 240 return -EAGAIN; 241 case RCODE_DATA_ERROR: 242 return -EREMOTEIO; 243 case RCODE_TYPE_ERROR: 244 return -EACCES; 245 case RCODE_ADDRESS_ERROR: 246 return -EINVAL; 247 default: 248 HPSB_ERR("received reserved rcode %d from node %d", 249 (packet->header[1] >> 12) & 0xf, 250 packet->node_id); 251 return -EAGAIN; 252 } 253 HPSB_PANIC("reached unreachable code 1 in %s", __FUNCTION__); 254 255 case ACK_BUSY_X: 256 case ACK_BUSY_A: 257 case ACK_BUSY_B: 258 return -EBUSY; 259 260 case ACK_TYPE_ERROR: 261 return -EACCES; 262 263 case ACK_COMPLETE: 264 if (packet->tcode == TCODE_WRITEQ 265 || packet->tcode == TCODE_WRITEB) { 266 return 0; 267 } else { 268 HPSB_ERR("impossible ack_complete from node %d " 269 "(tcode %d)", packet->node_id, packet->tcode); 270 return -EAGAIN; 271 } 272 273 274 case ACK_DATA_ERROR: 275 if (packet->tcode == TCODE_WRITEB 276 || packet->tcode == TCODE_LOCK_REQUEST) { 277 return -EAGAIN; 278 } else { 279 HPSB_ERR("impossible ack_data_error from node %d " 280 "(tcode %d)", packet->node_id, packet->tcode); 281 return -EAGAIN; 282 } 283 284 case ACKX_NONE: 285 case ACKX_SEND_ERROR: 286 case ACKX_ABORTED: 287 case ACKX_TIMEOUT: 288 /* error while sending */ 289 return -EAGAIN; 290 291 default: 292 HPSB_ERR("got invalid ack %d from node %d (tcode %d)", 293 packet->ack_code, packet->node_id, packet->tcode); 294 return -EAGAIN; 295 } 296 297 HPSB_PANIC("reached unreachable code 2 in %s", __FUNCTION__); 298} 299 300 301int hpsb_read_trylocal(struct hpsb_host *host, nodeid_t node, u64 addr, 302 quadlet_t *buffer, size_t length) 303{ 304 if (host->node_id != node) return -1; 305 return highlevel_read(host, node, buffer, addr, length); 306} 307 308struct hpsb_packet *hpsb_make_readqpacket(struct hpsb_host *host, nodeid_t node, 309 u64 addr) 310{ 311 struct hpsb_packet *p; 312 313 p = alloc_hpsb_packet(0); 314 if (!p) return NULL; 315 316 p->host = host; 317 p->tlabel = get_tlabel(host, node, 1); 318 p->node_id = node; 319 fill_async_readquad(p, addr); 320 321 return p; 322} 323 324struct hpsb_packet *hpsb_make_readbpacket(struct hpsb_host *host, nodeid_t node, 325 u64 addr, size_t length) 326{ 327 struct hpsb_packet *p; 328 329 p = alloc_hpsb_packet(length + (length % 4 ? 4 - (length % 4) : 0)); 330 if (!p) return NULL; 331 332 p->host = host; 333 p->tlabel = get_tlabel(host, node, 1); 334 p->node_id = node; 335 fill_async_readblock(p, addr, length); 336 337 return p; 338} 339 340struct hpsb_packet *hpsb_make_writeqpacket(struct hpsb_host *host, 341 nodeid_t node, u64 addr, 342 quadlet_t data) 343{ 344 struct hpsb_packet *p; 345 346 p = alloc_hpsb_packet(0); 347 if (!p) return NULL; 348 349 p->host = host; 350 p->tlabel = get_tlabel(host, node, 1); 351 p->node_id = node; 352 fill_async_writequad(p, addr, data); 353 354 return p; 355} 356 357struct hpsb_packet *hpsb_make_writebpacket(struct hpsb_host *host, 358 nodeid_t node, u64 addr, 359 size_t length) 360{ 361 struct hpsb_packet *p; 362 363 p = alloc_hpsb_packet(length + (length % 4 ? 4 - (length % 4) : 0)); 364 if (!p) return NULL; 365 366 if (length % 4) { 367 p->data[length / 4] = 0; 368 } 369 370 p->host = host; 371 p->tlabel = get_tlabel(host, node, 1); 372 p->node_id = node; 373 fill_async_writeblock(p, addr, length); 374 375 return p; 376} 377 378struct hpsb_packet *hpsb_make_lockpacket(struct hpsb_host *host, nodeid_t node, 379 u64 addr, int extcode) 380{ 381 struct hpsb_packet *p; 382 383 p = alloc_hpsb_packet(8); 384 if (!p) return NULL; 385 386 p->host = host; 387 p->tlabel = get_tlabel(host, node, 1); 388 p->node_id = node; 389 390 switch (extcode) { 391 case EXTCODE_FETCH_ADD: 392 case EXTCODE_LITTLE_ADD: 393 fill_async_lock(p, addr, extcode, 4); 394 break; 395 default: 396 fill_async_lock(p, addr, extcode, 8); 397 break; 398 } 399 400 return p; 401} 402 403struct hpsb_packet *hpsb_make_phypacket(struct hpsb_host *host, 404 quadlet_t data) 405{ 406 struct hpsb_packet *p; 407 408 p = alloc_hpsb_packet(0); 409 if (!p) return NULL; 410 411 p->host = host; 412 fill_phy_packet(p, data); 413 414 return p; 415} 416 417 418int hpsb_read(struct hpsb_host *host, nodeid_t node, unsigned int generation, 419 u64 addr, quadlet_t *buffer, size_t length) 420{ 421 struct hpsb_packet *packet; 422 int retval = 0; 423 424 if (length == 0) { 425 return -EINVAL; 426 } 427 428 if (host->node_id == node) { 429 switch(highlevel_read(host, node, buffer, addr, length)) { 430 case RCODE_COMPLETE: 431 return 0; 432 case RCODE_TYPE_ERROR: 433 return -EACCES; 434 case RCODE_ADDRESS_ERROR: 435 default: 436 return -EINVAL; 437 } 438 } 439 440 if (length == 4) { 441 packet = hpsb_make_readqpacket(host, node, addr); 442 } else { 443 packet = hpsb_make_readbpacket(host, node, addr, length); 444 } 445 446 if (!packet) { 447 return -ENOMEM; 448 } 449 450 packet->generation = generation; 451 if (!hpsb_send_packet(packet)) { 452 retval = -EINVAL; 453 goto hpsb_read_fail; 454 } 455 456 down(&packet->state_change); 457 down(&packet->state_change); 458 retval = hpsb_packet_success(packet); 459 460 if (retval == 0) { 461 if (length == 4) { 462 *buffer = packet->header[3]; 463 } else { 464 memcpy(buffer, packet->data, length); 465 } 466 } 467 468hpsb_read_fail: 469 free_tlabel(host, node, packet->tlabel); 470 free_hpsb_packet(packet); 471 472 return retval; 473} 474 475struct hpsb_packet *hpsb_make_packet (struct hpsb_host *host, nodeid_t node, 476 u64 addr, quadlet_t *buffer, size_t length) 477{ 478 struct hpsb_packet *packet; 479 480 if (length == 0) 481 return NULL; 482 483 if (length == 4) 484 packet = hpsb_make_writeqpacket(host, node, addr, *buffer); 485 else 486 packet = hpsb_make_writebpacket(host, node, addr, length); 487 488 if (!packet) 489 return NULL; 490 491 /* Sometimes this may be called without data, just to allocate the 492 * packet. */ 493 if (length != 4 && buffer) 494 memcpy(packet->data, buffer, length); 495 496 return packet; 497} 498 499int hpsb_write(struct hpsb_host *host, nodeid_t node, unsigned int generation, 500 u64 addr, quadlet_t *buffer, size_t length) 501{ 502 struct hpsb_packet *packet; 503 int retval; 504 505 if (length == 0) 506 return -EINVAL; 507 508 if (host->node_id == node) { 509 switch(highlevel_write(host, node, node, buffer, addr, length)) { 510 case RCODE_COMPLETE: 511 return 0; 512 case RCODE_TYPE_ERROR: 513 return -EACCES; 514 case RCODE_ADDRESS_ERROR: 515 default: 516 return -EINVAL; 517 } 518 } 519 520 packet = hpsb_make_packet (host, node, addr, buffer, length); 521 522 if (!packet) 523 return -ENOMEM; 524 525 packet->generation = generation; 526 if (!hpsb_send_packet(packet)) { 527 retval = -EINVAL; 528 goto hpsb_write_fail; 529 } 530 531 down(&packet->state_change); 532 down(&packet->state_change); 533 retval = hpsb_packet_success(packet); 534 535hpsb_write_fail: 536 free_tlabel(host, node, packet->tlabel); 537 free_hpsb_packet(packet); 538 539 return retval; 540} 541 542 543/* We need a hpsb_lock64 function for the 64 bit equivalent. Probably. */ 544int hpsb_lock(struct hpsb_host *host, nodeid_t node, unsigned int generation, 545 u64 addr, int extcode, quadlet_t *data, quadlet_t arg) 546{ 547 struct hpsb_packet *packet; 548 int retval = 0, length; 549 550 if (host->node_id == node) { 551 switch(highlevel_lock(host, node, data, addr, *data, arg, 552 extcode)) { 553 case RCODE_COMPLETE: 554 return 0; 555 case RCODE_TYPE_ERROR: 556 return -EACCES; 557 case RCODE_ADDRESS_ERROR: 558 default: 559 return -EINVAL; 560 } 561 } 562 563 packet = alloc_hpsb_packet(8); 564 if (!packet) { 565 return -ENOMEM; 566 } 567 568 packet->host = host; 569 packet->tlabel = get_tlabel(host, node, 1); 570 packet->node_id = node; 571 572 switch (extcode) { 573 case EXTCODE_MASK_SWAP: 574 case EXTCODE_COMPARE_SWAP: 575 case EXTCODE_BOUNDED_ADD: 576 case EXTCODE_WRAP_ADD: 577 length = 8; 578 packet->data[0] = arg; 579 packet->data[1] = *data; 580 break; 581 case EXTCODE_FETCH_ADD: 582 case EXTCODE_LITTLE_ADD: 583 length = 4; 584 packet->data[0] = *data; 585 break; 586 default: 587 return -EINVAL; 588 } 589 fill_async_lock(packet, addr, extcode, length); 590 591 packet->generation = generation; 592 if (!hpsb_send_packet(packet)) { 593 retval = -EINVAL; 594 goto hpsb_lock_fail; 595 } 596 down(&packet->state_change); 597 down(&packet->state_change); 598 retval = hpsb_packet_success(packet); 599 600 if (retval == 0) { 601 *data = packet->data[0]; 602 } 603 604hpsb_lock_fail: 605 free_tlabel(host, node, packet->tlabel); 606 free_hpsb_packet(packet); 607 608 return retval; 609} 610