1 // SPDX-License-Identifier: GPL-2.0+
5 * The state machine for an Open IPMI BT sub-driver under ipmi_si.c, part
6 * of the driver architecture at http://sourceforge.net/projects/openipmi
8 * Author: Rocky Craig <first.last@hp.com>
11 #include <linux/kernel.h> /* For printk. */
12 #include <linux/string.h>
13 #include <linux/module.h>
14 #include <linux/moduleparam.h>
15 #include <linux/ipmi_msgdefs.h> /* for completion codes */
16 #include "ipmi_si_sm.h"
18 #define BT_DEBUG_OFF 0 /* Used in production */
19 #define BT_DEBUG_ENABLE 1 /* Generic messages */
20 #define BT_DEBUG_MSG 2 /* Prints all request/response buffers */
21 #define BT_DEBUG_STATES 4 /* Verbose look at state changes */
23 * BT_DEBUG_OFF must be zero to correspond to the default uninitialized
27 static int bt_debug
; /* 0 == BT_DEBUG_OFF */
29 module_param(bt_debug
, int, 0644);
30 MODULE_PARM_DESC(bt_debug
, "debug bitmask, 1=enable, 2=messages, 4=states");
33 * Typical "Get BT Capabilities" values are 2-3 retries, 5-10 seconds,
34 * and 64 byte buffers. However, one HP implementation wants 255 bytes of
35 * buffer (with a documented message of 160 bytes) so go for the max.
36 * Since the Open IPMI architecture is single-message oriented at this
37 * stage, the queue depth of BT is of no concern.
40 #define BT_NORMAL_TIMEOUT 5 /* seconds */
41 #define BT_NORMAL_RETRY_LIMIT 2
42 #define BT_RESET_DELAY 6 /* seconds after warm reset */
45 * States are written in chronological order and usually cover
46 * multiple rows of the state table discussion in the IPMI spec.
50 BT_STATE_IDLE
= 0, /* Order is critical in this list */
51 BT_STATE_XACTION_START
,
53 BT_STATE_WRITE_CONSUME
,
57 BT_STATE_RESET1
, /* These must come last */
62 BT_STATE_LONG_BUSY
/* BT doesn't get hosed :-) */
66 * Macros seen at the end of state "case" blocks. They help with legibility
70 #define BT_STATE_CHANGE(X, Y) { bt->state = X; return Y; }
72 #define BT_SI_SM_RETURN(Y) { last_printed = BT_STATE_PRINTME; return Y; }
76 unsigned char seq
; /* BT sequence number */
78 unsigned char write_data
[IPMI_MAX_MSG_LENGTH
+ 2]; /* +2 for memcpy */
80 unsigned char read_data
[IPMI_MAX_MSG_LENGTH
+ 2]; /* +2 for memcpy */
83 long timeout
; /* microseconds countdown */
84 int error_retries
; /* end of "common" fields */
85 int nonzero_status
; /* hung BMCs stay all 0 */
86 enum bt_states complete
; /* to divert the state machine */
88 int BT_CAP_retries
; /* Recommended retries */
91 #define BT_CLR_WR_PTR 0x01 /* See IPMI 1.5 table 11.6.4 */
92 #define BT_CLR_RD_PTR 0x02
93 #define BT_H2B_ATN 0x04
94 #define BT_B2H_ATN 0x08
95 #define BT_SMS_ATN 0x10
97 #define BT_H_BUSY 0x40
98 #define BT_B_BUSY 0x80
101 * Some bits are toggled on each write: write once to set it, once
102 * more to clear it; writing a zero does nothing. To absolutely
103 * clear it, check its state and write if set. This avoids the "get
104 * current then use as mask" scheme to modify one bit. Note that the
105 * variable "bt" is hardcoded into these macros.
108 #define BT_STATUS bt->io->inputb(bt->io, 0)
109 #define BT_CONTROL(x) bt->io->outputb(bt->io, 0, x)
111 #define BMC2HOST bt->io->inputb(bt->io, 1)
112 #define HOST2BMC(x) bt->io->outputb(bt->io, 1, x)
114 #define BT_INTMASK_R bt->io->inputb(bt->io, 2)
115 #define BT_INTMASK_W(x) bt->io->outputb(bt->io, 2, x)
118 * Convenience routines for debugging. These are not multi-open safe!
119 * Note the macros have hardcoded variables in them.
122 static char *state2txt(unsigned char state
)
125 case BT_STATE_IDLE
: return("IDLE");
126 case BT_STATE_XACTION_START
: return("XACTION");
127 case BT_STATE_WRITE_BYTES
: return("WR_BYTES");
128 case BT_STATE_WRITE_CONSUME
: return("WR_CONSUME");
129 case BT_STATE_READ_WAIT
: return("RD_WAIT");
130 case BT_STATE_CLEAR_B2H
: return("CLEAR_B2H");
131 case BT_STATE_READ_BYTES
: return("RD_BYTES");
132 case BT_STATE_RESET1
: return("RESET1");
133 case BT_STATE_RESET2
: return("RESET2");
134 case BT_STATE_RESET3
: return("RESET3");
135 case BT_STATE_RESTART
: return("RESTART");
136 case BT_STATE_LONG_BUSY
: return("LONG_BUSY");
140 #define STATE2TXT state2txt(bt->state)
142 static char *status2txt(unsigned char status
)
145 * This cannot be called by two threads at the same time and
146 * the buffer is always consumed immediately, so the static is
152 if (status
& BT_B_BUSY
)
153 strcat(buf
, "B_BUSY ");
154 if (status
& BT_H_BUSY
)
155 strcat(buf
, "H_BUSY ");
156 if (status
& BT_OEM0
)
157 strcat(buf
, "OEM0 ");
158 if (status
& BT_SMS_ATN
)
160 if (status
& BT_B2H_ATN
)
162 if (status
& BT_H2B_ATN
)
167 #define STATUS2TXT status2txt(status)
169 /* called externally at insmod time, and internally on cleanup */
171 static unsigned int bt_init_data(struct si_sm_data
*bt
, struct si_sm_io
*io
)
173 memset(bt
, 0, sizeof(struct si_sm_data
));
175 /* external: one-time only things */
179 bt
->state
= BT_STATE_IDLE
; /* start here */
180 bt
->complete
= BT_STATE_IDLE
; /* end here */
181 bt
->BT_CAP_req2rsp
= BT_NORMAL_TIMEOUT
* USEC_PER_SEC
;
182 bt
->BT_CAP_retries
= BT_NORMAL_RETRY_LIMIT
;
183 return 3; /* We claim 3 bytes of space; ought to check SPMI table */
186 /* Jam a completion code (probably an error) into a response */
188 static void force_result(struct si_sm_data
*bt
, unsigned char completion_code
)
190 bt
->read_data
[0] = 4; /* # following bytes */
191 bt
->read_data
[1] = bt
->write_data
[1] | 4; /* Odd NetFn/LUN */
192 bt
->read_data
[2] = bt
->write_data
[2]; /* seq (ignored) */
193 bt
->read_data
[3] = bt
->write_data
[3]; /* Command */
194 bt
->read_data
[4] = completion_code
;
198 /* The upper state machine starts here */
200 static int bt_start_transaction(struct si_sm_data
*bt
,
207 return IPMI_REQ_LEN_INVALID_ERR
;
208 if (size
> IPMI_MAX_MSG_LENGTH
)
209 return IPMI_REQ_LEN_EXCEEDED_ERR
;
211 if (bt
->state
== BT_STATE_LONG_BUSY
)
212 return IPMI_NODE_BUSY_ERR
;
214 if (bt
->state
!= BT_STATE_IDLE
)
215 return IPMI_NOT_IN_MY_STATE_ERR
;
217 if (bt_debug
& BT_DEBUG_MSG
) {
218 printk(KERN_WARNING
"BT: +++++++++++++++++ New command\n");
219 printk(KERN_WARNING
"BT: NetFn/LUN CMD [%d data]:", size
- 2);
220 for (i
= 0; i
< size
; i
++)
221 printk(" %02x", data
[i
]);
224 bt
->write_data
[0] = size
+ 1; /* all data plus seq byte */
225 bt
->write_data
[1] = *data
; /* NetFn/LUN */
226 bt
->write_data
[2] = bt
->seq
++;
227 memcpy(bt
->write_data
+ 3, data
+ 1, size
- 1);
228 bt
->write_count
= size
+ 2;
229 bt
->error_retries
= 0;
230 bt
->nonzero_status
= 0;
232 bt
->state
= BT_STATE_XACTION_START
;
233 bt
->timeout
= bt
->BT_CAP_req2rsp
;
234 force_result(bt
, IPMI_ERR_UNSPECIFIED
);
239 * After the upper state machine has been told SI_SM_TRANSACTION_COMPLETE
240 * it calls this. Strip out the length and seq bytes.
243 static int bt_get_result(struct si_sm_data
*bt
,
249 msg_len
= bt
->read_count
- 2; /* account for length & seq */
250 if (msg_len
< 3 || msg_len
> IPMI_MAX_MSG_LENGTH
) {
251 force_result(bt
, IPMI_ERR_UNSPECIFIED
);
254 data
[0] = bt
->read_data
[1];
255 data
[1] = bt
->read_data
[3];
256 if (length
< msg_len
|| bt
->truncated
) {
257 data
[2] = IPMI_ERR_MSG_TRUNCATED
;
260 memcpy(data
+ 2, bt
->read_data
+ 4, msg_len
- 2);
262 if (bt_debug
& BT_DEBUG_MSG
) {
263 printk(KERN_WARNING
"BT: result %d bytes:", msg_len
);
264 for (i
= 0; i
< msg_len
; i
++)
265 printk(" %02x", data
[i
]);
271 /* This bit's functionality is optional */
272 #define BT_BMC_HWRST 0x80
274 static void reset_flags(struct si_sm_data
*bt
)
277 printk(KERN_WARNING
"IPMI BT: flag reset %s\n",
278 status2txt(BT_STATUS
));
279 if (BT_STATUS
& BT_H_BUSY
)
280 BT_CONTROL(BT_H_BUSY
); /* force clear */
281 BT_CONTROL(BT_CLR_WR_PTR
); /* always reset */
282 BT_CONTROL(BT_SMS_ATN
); /* always clear */
283 BT_INTMASK_W(BT_BMC_HWRST
);
287 * Get rid of an unwanted/stale response. This should only be needed for
288 * BMCs that support multiple outstanding requests.
291 static void drain_BMC2HOST(struct si_sm_data
*bt
)
295 if (!(BT_STATUS
& BT_B2H_ATN
)) /* Not signalling a response */
298 BT_CONTROL(BT_H_BUSY
); /* now set */
299 BT_CONTROL(BT_B2H_ATN
); /* always clear */
300 BT_STATUS
; /* pause */
301 BT_CONTROL(BT_B2H_ATN
); /* some BMCs are stubborn */
302 BT_CONTROL(BT_CLR_RD_PTR
); /* always reset */
304 printk(KERN_WARNING
"IPMI BT: stale response %s; ",
305 status2txt(BT_STATUS
));
307 for (i
= 0; i
< size
; i
++)
309 BT_CONTROL(BT_H_BUSY
); /* now clear */
311 printk("drained %d bytes\n", size
+ 1);
314 static inline void write_all_bytes(struct si_sm_data
*bt
)
318 if (bt_debug
& BT_DEBUG_MSG
) {
319 printk(KERN_WARNING
"BT: write %d bytes seq=0x%02X",
320 bt
->write_count
, bt
->seq
);
321 for (i
= 0; i
< bt
->write_count
; i
++)
322 printk(" %02x", bt
->write_data
[i
]);
325 for (i
= 0; i
< bt
->write_count
; i
++)
326 HOST2BMC(bt
->write_data
[i
]);
329 static inline int read_all_bytes(struct si_sm_data
*bt
)
334 * length is "framing info", minimum = 4: NetFn, Seq, Cmd, cCode.
335 * Keep layout of first four bytes aligned with write_data[]
338 bt
->read_data
[0] = BMC2HOST
;
339 bt
->read_count
= bt
->read_data
[0];
341 if (bt
->read_count
< 4 || bt
->read_count
>= IPMI_MAX_MSG_LENGTH
) {
342 if (bt_debug
& BT_DEBUG_MSG
)
343 printk(KERN_WARNING
"BT: bad raw rsp len=%d\n",
346 return 1; /* let next XACTION START clean it up */
348 for (i
= 1; i
<= bt
->read_count
; i
++)
349 bt
->read_data
[i
] = BMC2HOST
;
350 bt
->read_count
++; /* Account internally for length byte */
352 if (bt_debug
& BT_DEBUG_MSG
) {
353 int max
= bt
->read_count
;
355 printk(KERN_WARNING
"BT: got %d bytes seq=0x%02X",
356 max
, bt
->read_data
[2]);
359 for (i
= 0; i
< max
; i
++)
360 printk(KERN_CONT
" %02x", bt
->read_data
[i
]);
361 printk(KERN_CONT
"%s\n", bt
->read_count
== max
? "" : " ...");
364 /* per the spec, the (NetFn[1], Seq[2], Cmd[3]) tuples must match */
365 if ((bt
->read_data
[3] == bt
->write_data
[3]) &&
366 (bt
->read_data
[2] == bt
->write_data
[2]) &&
367 ((bt
->read_data
[1] & 0xF8) == (bt
->write_data
[1] & 0xF8)))
370 if (bt_debug
& BT_DEBUG_MSG
)
371 printk(KERN_WARNING
"IPMI BT: bad packet: "
372 "want 0x(%02X, %02X, %02X) got (%02X, %02X, %02X)\n",
373 bt
->write_data
[1] | 0x04, bt
->write_data
[2], bt
->write_data
[3],
374 bt
->read_data
[1], bt
->read_data
[2], bt
->read_data
[3]);
378 /* Restart if retries are left, or return an error completion code */
380 static enum si_sm_result
error_recovery(struct si_sm_data
*bt
,
381 unsigned char status
,
386 bt
->timeout
= bt
->BT_CAP_req2rsp
;
389 case IPMI_TIMEOUT_ERR
:
393 reason
= "internal error";
397 printk(KERN_WARNING
"IPMI BT: %s in %s %s ", /* open-ended line */
398 reason
, STATE2TXT
, STATUS2TXT
);
401 * Per the IPMI spec, retries are based on the sequence number
402 * known only to this module, so manage a restart here.
404 (bt
->error_retries
)++;
405 if (bt
->error_retries
< bt
->BT_CAP_retries
) {
406 printk("%d retries left\n",
407 bt
->BT_CAP_retries
- bt
->error_retries
);
408 bt
->state
= BT_STATE_RESTART
;
409 return SI_SM_CALL_WITHOUT_DELAY
;
412 printk(KERN_WARNING
"failed %d retries, sending error response\n",
414 if (!bt
->nonzero_status
)
415 printk(KERN_ERR
"IPMI BT: stuck, try power cycle\n");
417 /* this is most likely during insmod */
418 else if (bt
->seq
<= (unsigned char)(bt
->BT_CAP_retries
& 0xFF)) {
419 printk(KERN_WARNING
"IPMI: BT reset (takes 5 secs)\n");
420 bt
->state
= BT_STATE_RESET1
;
421 return SI_SM_CALL_WITHOUT_DELAY
;
425 * Concoct a useful error message, set up the next state, and
426 * be done with this sequence.
429 bt
->state
= BT_STATE_IDLE
;
431 case IPMI_TIMEOUT_ERR
:
432 if (status
& BT_B_BUSY
) {
433 cCode
= IPMI_NODE_BUSY_ERR
;
434 bt
->state
= BT_STATE_LONG_BUSY
;
440 force_result(bt
, cCode
);
441 return SI_SM_TRANSACTION_COMPLETE
;
444 /* Check status and (usually) take action and change this state machine. */
446 static enum si_sm_result
bt_event(struct si_sm_data
*bt
, long time
)
448 unsigned char status
;
449 static enum bt_states last_printed
= BT_STATE_PRINTME
;
453 bt
->nonzero_status
|= status
;
454 if ((bt_debug
& BT_DEBUG_STATES
) && (bt
->state
!= last_printed
)) {
455 printk(KERN_WARNING
"BT: %s %s TO=%ld - %ld \n",
460 last_printed
= bt
->state
;
464 * Commands that time out may still (eventually) provide a response.
465 * This stale response will get in the way of a new response so remove
466 * it if possible (hopefully during IDLE). Even if it comes up later
467 * it will be rejected by its (now-forgotten) seq number.
470 if ((bt
->state
< BT_STATE_WRITE_BYTES
) && (status
& BT_B2H_ATN
)) {
472 BT_SI_SM_RETURN(SI_SM_CALL_WITH_DELAY
);
475 if ((bt
->state
!= BT_STATE_IDLE
) &&
476 (bt
->state
< BT_STATE_PRINTME
)) {
479 if ((bt
->timeout
< 0) && (bt
->state
< BT_STATE_RESET1
))
480 return error_recovery(bt
,
488 * Idle state first checks for asynchronous messages from another
489 * channel, then does some opportunistic housekeeping.
493 if (status
& BT_SMS_ATN
) {
494 BT_CONTROL(BT_SMS_ATN
); /* clear it */
498 if (status
& BT_H_BUSY
) /* clear a leftover H_BUSY */
499 BT_CONTROL(BT_H_BUSY
);
501 BT_SI_SM_RETURN(SI_SM_IDLE
);
503 case BT_STATE_XACTION_START
:
504 if (status
& (BT_B_BUSY
| BT_H2B_ATN
))
505 BT_SI_SM_RETURN(SI_SM_CALL_WITH_DELAY
);
506 if (BT_STATUS
& BT_H_BUSY
)
507 BT_CONTROL(BT_H_BUSY
); /* force clear */
508 BT_STATE_CHANGE(BT_STATE_WRITE_BYTES
,
509 SI_SM_CALL_WITHOUT_DELAY
);
511 case BT_STATE_WRITE_BYTES
:
512 if (status
& BT_H_BUSY
)
513 BT_CONTROL(BT_H_BUSY
); /* clear */
514 BT_CONTROL(BT_CLR_WR_PTR
);
516 BT_CONTROL(BT_H2B_ATN
); /* can clear too fast to catch */
517 BT_STATE_CHANGE(BT_STATE_WRITE_CONSUME
,
518 SI_SM_CALL_WITHOUT_DELAY
);
520 case BT_STATE_WRITE_CONSUME
:
521 if (status
& (BT_B_BUSY
| BT_H2B_ATN
))
522 BT_SI_SM_RETURN(SI_SM_CALL_WITH_DELAY
);
523 BT_STATE_CHANGE(BT_STATE_READ_WAIT
,
524 SI_SM_CALL_WITHOUT_DELAY
);
526 /* Spinning hard can suppress B2H_ATN and force a timeout */
528 case BT_STATE_READ_WAIT
:
529 if (!(status
& BT_B2H_ATN
))
530 BT_SI_SM_RETURN(SI_SM_CALL_WITH_DELAY
);
531 BT_CONTROL(BT_H_BUSY
); /* set */
534 * Uncached, ordered writes should just proceed serially but
535 * some BMCs don't clear B2H_ATN with one hit. Fast-path a
536 * workaround without too much penalty to the general case.
539 BT_CONTROL(BT_B2H_ATN
); /* clear it to ACK the BMC */
540 BT_STATE_CHANGE(BT_STATE_CLEAR_B2H
,
541 SI_SM_CALL_WITHOUT_DELAY
);
543 case BT_STATE_CLEAR_B2H
:
544 if (status
& BT_B2H_ATN
) {
545 /* keep hitting it */
546 BT_CONTROL(BT_B2H_ATN
);
547 BT_SI_SM_RETURN(SI_SM_CALL_WITH_DELAY
);
549 BT_STATE_CHANGE(BT_STATE_READ_BYTES
,
550 SI_SM_CALL_WITHOUT_DELAY
);
552 case BT_STATE_READ_BYTES
:
553 if (!(status
& BT_H_BUSY
))
554 /* check in case of retry */
555 BT_CONTROL(BT_H_BUSY
);
556 BT_CONTROL(BT_CLR_RD_PTR
); /* start of BMC2HOST buffer */
557 i
= read_all_bytes(bt
); /* true == packet seq match */
558 BT_CONTROL(BT_H_BUSY
); /* NOW clear */
559 if (!i
) /* Not my message */
560 BT_STATE_CHANGE(BT_STATE_READ_WAIT
,
561 SI_SM_CALL_WITHOUT_DELAY
);
562 bt
->state
= bt
->complete
;
563 return bt
->state
== BT_STATE_IDLE
? /* where to next? */
564 SI_SM_TRANSACTION_COMPLETE
: /* normal */
565 SI_SM_CALL_WITHOUT_DELAY
; /* Startup magic */
567 case BT_STATE_LONG_BUSY
: /* For example: after FW update */
568 if (!(status
& BT_B_BUSY
)) {
569 reset_flags(bt
); /* next state is now IDLE */
570 bt_init_data(bt
, bt
->io
);
572 return SI_SM_CALL_WITH_DELAY
; /* No repeat printing */
574 case BT_STATE_RESET1
:
577 BT_STATE_CHANGE(BT_STATE_RESET2
,
578 SI_SM_CALL_WITH_DELAY
);
580 case BT_STATE_RESET2
: /* Send a soft reset */
581 BT_CONTROL(BT_CLR_WR_PTR
);
582 HOST2BMC(3); /* number of bytes following */
583 HOST2BMC(0x18); /* NetFn/LUN == Application, LUN 0 */
584 HOST2BMC(42); /* Sequence number */
585 HOST2BMC(3); /* Cmd == Soft reset */
586 BT_CONTROL(BT_H2B_ATN
);
587 bt
->timeout
= BT_RESET_DELAY
* USEC_PER_SEC
;
588 BT_STATE_CHANGE(BT_STATE_RESET3
,
589 SI_SM_CALL_WITH_DELAY
);
591 case BT_STATE_RESET3
: /* Hold off everything for a bit */
593 return SI_SM_CALL_WITH_DELAY
;
595 BT_STATE_CHANGE(BT_STATE_RESTART
,
596 SI_SM_CALL_WITH_DELAY
);
598 case BT_STATE_RESTART
: /* don't reset retries or seq! */
600 bt
->nonzero_status
= 0;
601 bt
->timeout
= bt
->BT_CAP_req2rsp
;
602 BT_STATE_CHANGE(BT_STATE_XACTION_START
,
603 SI_SM_CALL_WITH_DELAY
);
605 default: /* should never occur */
606 return error_recovery(bt
,
608 IPMI_ERR_UNSPECIFIED
);
610 return SI_SM_CALL_WITH_DELAY
;
613 static int bt_detect(struct si_sm_data
*bt
)
615 unsigned char GetBT_CAP
[] = { 0x18, 0x36 };
616 unsigned char BT_CAP
[8];
617 enum si_sm_result smi_result
;
621 * It's impossible for the BT status and interrupt registers to be
622 * all 1's, (assuming a properly functioning, self-initialized BMC)
623 * but that's what you get from reading a bogus address, so we
624 * test that first. The calling routine uses negative logic.
627 if ((BT_STATUS
== 0xFF) && (BT_INTMASK_R
== 0xFF))
632 * Try getting the BT capabilities here.
634 rv
= bt_start_transaction(bt
, GetBT_CAP
, sizeof(GetBT_CAP
));
636 dev_warn(bt
->io
->dev
,
637 "Can't start capabilities transaction: %d\n", rv
);
641 smi_result
= SI_SM_CALL_WITHOUT_DELAY
;
643 if (smi_result
== SI_SM_CALL_WITH_DELAY
||
644 smi_result
== SI_SM_CALL_WITH_TICK_DELAY
) {
645 schedule_timeout_uninterruptible(1);
646 smi_result
= bt_event(bt
, jiffies_to_usecs(1));
647 } else if (smi_result
== SI_SM_CALL_WITHOUT_DELAY
) {
648 smi_result
= bt_event(bt
, 0);
653 rv
= bt_get_result(bt
, BT_CAP
, sizeof(BT_CAP
));
654 bt_init_data(bt
, bt
->io
);
656 dev_warn(bt
->io
->dev
, "bt cap response too short: %d\n", rv
);
661 dev_warn(bt
->io
->dev
, "Error fetching bt cap: %x\n", BT_CAP
[2]);
663 dev_warn(bt
->io
->dev
, "using default values\n");
665 bt
->BT_CAP_req2rsp
= BT_CAP
[6] * USEC_PER_SEC
;
666 bt
->BT_CAP_retries
= BT_CAP
[7];
669 dev_info(bt
->io
->dev
, "req2rsp=%ld secs retries=%d\n",
670 bt
->BT_CAP_req2rsp
/ USEC_PER_SEC
, bt
->BT_CAP_retries
);
675 static void bt_cleanup(struct si_sm_data
*bt
)
679 static int bt_size(void)
681 return sizeof(struct si_sm_data
);
684 const struct si_sm_handlers bt_smi_handlers
= {
685 .init_data
= bt_init_data
,
686 .start_transaction
= bt_start_transaction
,
687 .get_result
= bt_get_result
,
690 .cleanup
= bt_cleanup
,