tinygo.org/x/drivers@v0.27.1-0.20240509133757-7dbca2a54349/mcp2515/mcp2515.go (about)

     1  // Package mcp2515 implements a driver for the MCP2515 CAN Controller.
     2  //
     3  // Datasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/MCP2515-Stand-Alone-CAN-Controller-with-SPI-20001801J.pdf
     4  //
     5  // Reference: https://github.com/coryjfowler/MCP_CAN_lib
     6  package mcp2515 // import "tinygo.org/x/drivers/mcp2515"
     7  
     8  import (
     9  	"errors"
    10  	"fmt"
    11  	"machine"
    12  	"time"
    13  
    14  	"tinygo.org/x/drivers"
    15  )
    16  
    17  // Device wraps MCP2515 SPI CAN Module.
    18  type Device struct {
    19  	spi     SPI
    20  	cs      machine.Pin
    21  	msg     *CANMsg
    22  	mcpMode byte
    23  }
    24  
    25  // CANMsg stores CAN message fields.
    26  type CANMsg struct {
    27  	ID   uint32
    28  	Dlc  uint8
    29  	Data []byte
    30  	Ext  bool
    31  	Rtr  bool
    32  }
    33  
    34  const (
    35  	bufferSize int = 64
    36  )
    37  
    38  // New returns a new MCP2515 driver. Pass in a fully configured SPI bus.
    39  func New(b drivers.SPI, csPin machine.Pin) *Device {
    40  	d := &Device{
    41  		spi: SPI{
    42  			bus: b,
    43  			tx:  make([]byte, 0, bufferSize),
    44  			rx:  make([]byte, 0, bufferSize),
    45  		},
    46  		cs:  csPin,
    47  		msg: &CANMsg{},
    48  	}
    49  
    50  	return d
    51  }
    52  
    53  // Configure sets up the device for communication.
    54  func (d *Device) Configure() {
    55  	d.cs.Configure(machine.PinConfig{Mode: machine.PinOutput})
    56  }
    57  
    58  const beginTimeoutValue int = 10
    59  
    60  // Begin starts the CAN controller.
    61  func (d *Device) Begin(speed byte, clock byte) error {
    62  	timeOutCount := 0
    63  	for {
    64  		err := d.init(speed, clock)
    65  		if err == nil {
    66  			break
    67  		}
    68  		timeOutCount++
    69  		if timeOutCount >= beginTimeoutValue {
    70  			return err
    71  		}
    72  	}
    73  	return nil
    74  }
    75  
    76  // Received returns true if CAN message is received.
    77  func (d *Device) Received() bool {
    78  	res, err := d.readStatus()
    79  	if err != nil {
    80  		panic(err)
    81  	}
    82  	// if RX STATUS INSTRUCTION  result is not 0x00 (= No RX message)
    83  	// TODO: reconsider this logic
    84  	return (res & mcpStatRxifMask) != 0x00
    85  }
    86  
    87  // Rx returns received CAN message.
    88  func (d *Device) Rx() (*CANMsg, error) {
    89  	err := d.readMsg()
    90  	return d.msg, err
    91  }
    92  
    93  // Tx transmits CAN Message.
    94  func (d *Device) Tx(canid uint32, dlc uint8, data []byte) error {
    95  	// TODO: add ext, rtrBit, waitSent
    96  	timeoutCount := 0
    97  
    98  	var bufNum, res uint8
    99  	var err error
   100  	res = mcpAlltxbusy
   101  	for res == mcpAlltxbusy && (timeoutCount < timeoutvalue) {
   102  		if timeoutCount > 0 {
   103  			time.Sleep(time.Microsecond * 10)
   104  		}
   105  		bufNum, res, err = d.getNextFreeTxBuf()
   106  		if err != nil {
   107  			return err
   108  		}
   109  		timeoutCount++
   110  	}
   111  	if timeoutCount == timeoutvalue {
   112  		return fmt.Errorf("Tx: Tx timeout")
   113  	}
   114  	err = d.writeCANMsg(bufNum, canid, 0, 0, dlc, data)
   115  	if err != nil {
   116  		return err
   117  	}
   118  
   119  	return nil
   120  }
   121  
   122  func (d *Device) init(speed, clock byte) error {
   123  	err := d.Reset()
   124  	if err != nil {
   125  		return err
   126  	}
   127  
   128  	if err := d.setCANCTRLMode(modeConfig); err != nil {
   129  		return fmt.Errorf("setCANCTRLMode %s: ", err)
   130  	}
   131  	time.Sleep(time.Millisecond * 10)
   132  
   133  	// set baudrate
   134  	if err := d.configRate(speed, clock); err != nil {
   135  		return fmt.Errorf("configRate %s: ", err)
   136  	}
   137  	time.Sleep(time.Millisecond * 10)
   138  
   139  	if err := d.initCANBuffers(); err != nil {
   140  		return fmt.Errorf("initCANBuffers: %s ", err)
   141  	}
   142  	if err := d.setRegister(mcpCANINTE, mcpRX0IF|mcpRX1IF); err != nil {
   143  		return fmt.Errorf("setRegister: %s ", err)
   144  	}
   145  	if err := d.modifyRegister(mcpRXB0CTRL, mcpRxbRxMask|mcpRxbBuktMask, mcpRxbRxStdExt|mcpRxbBuktMask); err != nil {
   146  		return fmt.Errorf("modifyRegister: %s ", err)
   147  	}
   148  	if err := d.modifyRegister(mcpRXB1CTRL, mcpRxbRxMask, mcpRxbRxStdExt); err != nil {
   149  		return fmt.Errorf("modifyRegister: %s ", err)
   150  	}
   151  
   152  	if err := d.setMode(modeNormal); err != nil {
   153  		return fmt.Errorf("setMode %s: ", err)
   154  	}
   155  	time.Sleep(time.Millisecond * 10)
   156  
   157  	return nil
   158  }
   159  
   160  // Reset resets mcp2515.
   161  func (d *Device) Reset() error {
   162  	d.cs.Low()
   163  	_, err := d.spi.readWrite(mcpReset)
   164  	d.cs.High()
   165  	// time.Sleep(time.Microsecond * 4)
   166  	if err != nil {
   167  		return err
   168  	}
   169  
   170  	time.Sleep(time.Millisecond * 10)
   171  
   172  	return nil
   173  }
   174  
   175  func (d *Device) setCANCTRLMode(newMode byte) error {
   176  	// If the chip is asleep and we want to change mode then a manual wake needs to be done
   177  	// This is done by setting the wake up interrupt flag
   178  	// This undocumented trick was found at https://github.com/mkleemann/can/blob/master/can_sleep_mcp2515.c
   179  	m, err := d.getMode()
   180  	if err != nil {
   181  		return err
   182  	}
   183  	if m == modeSleep && newMode != modeSleep {
   184  		r, err := d.readRegister(mcpCANINTE)
   185  		if err != nil {
   186  			return err
   187  		}
   188  		wakeIntEnabled := (r & mcpWAKIF) == 0x00
   189  		if !wakeIntEnabled {
   190  			d.modifyRegister(mcpCANINTE, mcpWAKIF, mcpWAKIF)
   191  		}
   192  		// Set wake flag (this does the actual waking up)
   193  		d.modifyRegister(mcpCANINTF, mcpWAKIF, mcpWAKIF)
   194  
   195  		// Wait for the chip to exit SLEEP and enter LISTENONLY mode.
   196  
   197  		// If the chip is not connected to a CAN bus (or the bus has no other powered nodes) it will sometimes trigger the wake interrupt as soon
   198  		// as it's put to sleep, but it will stay in SLEEP mode instead of automatically switching to LISTENONLY mode.
   199  		// In this situation the mode needs to be manually set to LISTENONLY.
   200  
   201  		if err := d.requestNewMode(modeListenOnly); err != nil {
   202  			return err
   203  		}
   204  
   205  		// Turn wake interrupt back off if it was originally off
   206  		if !wakeIntEnabled {
   207  			d.modifyRegister(mcpCANINTE, mcpWAKIF, 0)
   208  		}
   209  	}
   210  
   211  	// Clear wake flag
   212  	d.modifyRegister(mcpCANINTF, mcpWAKIF, 0)
   213  
   214  	return d.requestNewMode(newMode)
   215  }
   216  
   217  func (d *Device) setMode(opMode byte) error {
   218  	if opMode != modeSleep {
   219  		d.mcpMode = opMode
   220  	}
   221  
   222  	err := d.setCANCTRLMode(opMode)
   223  	if err != nil {
   224  		return err
   225  	}
   226  
   227  	return nil
   228  }
   229  
   230  func (d *Device) getMode() (byte, error) {
   231  	r, err := d.readRegister(mcpCANSTAT)
   232  	if err != nil {
   233  		return 0, err
   234  	}
   235  	return r & modeMask, nil
   236  }
   237  
   238  func (d *Device) configRate(speed, clock byte) error {
   239  	var cfg1, cfg2, cfg3 byte
   240  	set := true
   241  	switch clock {
   242  	case Clock16MHz:
   243  		switch speed {
   244  		case CAN5kBps:
   245  			cfg1 = mcp16mHz5kBpsCfg1
   246  			cfg2 = mcp16mHz5kBpsCfg2
   247  			cfg3 = mcp16mHz5kBpsCfg3
   248  		case CAN10kBps:
   249  			cfg1 = mcp16mHz10kBpsCfg1
   250  			cfg2 = mcp16mHz10kBpsCfg2
   251  			cfg3 = mcp16mHz10kBpsCfg3
   252  		case CAN20kBps:
   253  			cfg1 = mcp16mHz20kBpsCfg1
   254  			cfg2 = mcp16mHz20kBpsCfg2
   255  			cfg3 = mcp16mHz20kBpsCfg3
   256  		case CAN25kBps:
   257  			cfg1 = mcp16mHz25kBpsCfg1
   258  			cfg2 = mcp16mHz25kBpsCfg2
   259  			cfg3 = mcp16mHz25kBpsCfg3
   260  		case CAN31k25Bps:
   261  			cfg1 = mcp16mHz31k25BpsCfg1
   262  			cfg2 = mcp16mHz31k25BpsCfg2
   263  			cfg3 = mcp16mHz31k25BpsCfg3
   264  		case CAN33kBps:
   265  			cfg1 = mcp16mHz33kBpsCfg1
   266  			cfg2 = mcp16mHz33kBpsCfg2
   267  			cfg3 = mcp16mHz33kBpsCfg3
   268  		case CAN40kBps:
   269  			cfg1 = mcp16mHz40kBpsCfg1
   270  			cfg2 = mcp16mHz40kBpsCfg2
   271  			cfg3 = mcp16mHz40kBpsCfg3
   272  		case CAN47kBps:
   273  			cfg1 = mcp16mHz47kBpsCfg1
   274  			cfg2 = mcp16mHz47kBpsCfg2
   275  			cfg3 = mcp16mHz47kBpsCfg3
   276  		case CAN50kBps:
   277  			cfg1 = mcp16mHz50kBpsCfg1
   278  			cfg2 = mcp16mHz50kBpsCfg2
   279  			cfg3 = mcp16mHz50kBpsCfg3
   280  		case CAN80kBps:
   281  			cfg1 = mcp16mHz80kBpsCfg1
   282  			cfg2 = mcp16mHz80kBpsCfg2
   283  			cfg3 = mcp16mHz80kBpsCfg3
   284  		case CAN83k3Bps:
   285  			cfg1 = mcp16mHz83k3BpsCfg1
   286  			cfg2 = mcp16mHz83k3BpsCfg2
   287  			cfg3 = mcp16mHz83k3BpsCfg3
   288  		case CAN95kBps:
   289  			cfg1 = mcp16mHz95kBpsCfg1
   290  			cfg2 = mcp16mHz95kBpsCfg2
   291  			cfg3 = mcp16mHz95kBpsCfg3
   292  		case CAN100kBps:
   293  			cfg1 = mcp16mHz100kBpsCfg1
   294  			cfg2 = mcp16mHz100kBpsCfg2
   295  			cfg3 = mcp16mHz100kBpsCfg3
   296  		case CAN125kBps:
   297  			cfg1 = mcp16mHz125kBpsCfg1
   298  			cfg2 = mcp16mHz125kBpsCfg2
   299  			cfg3 = mcp16mHz125kBpsCfg3
   300  		case CAN200kBps:
   301  			cfg1 = mcp16mHz200kBpsCfg1
   302  			cfg2 = mcp16mHz200kBpsCfg2
   303  			cfg3 = mcp16mHz200kBpsCfg3
   304  		case CAN250kBps:
   305  			cfg1 = mcp16mHz250kBpsCfg1
   306  			cfg2 = mcp16mHz250kBpsCfg2
   307  			cfg3 = mcp16mHz250kBpsCfg3
   308  		case CAN500kBps:
   309  			cfg1 = mcp16mHz500kBpsCfg1
   310  			cfg2 = mcp16mHz500kBpsCfg2
   311  			cfg3 = mcp16mHz500kBpsCfg3
   312  		case CAN666kBps:
   313  			cfg1 = mcp16mHz666kBpsCfg1
   314  			cfg2 = mcp16mHz666kBpsCfg2
   315  			cfg3 = mcp16mHz666kBpsCfg3
   316  		case CAN1000kBps:
   317  			cfg1 = mcp16mHz1000kBpsCfg1
   318  			cfg2 = mcp16mHz1000kBpsCfg2
   319  			cfg3 = mcp16mHz1000kBpsCfg3
   320  		default:
   321  			set = false
   322  		}
   323  	case Clock8MHz:
   324  		switch speed {
   325  		case CAN5kBps:
   326  			cfg1 = mcp8mHz5kBpsCfg1
   327  			cfg2 = mcp8mHz5kBpsCfg2
   328  			cfg3 = mcp8mHz5kBpsCfg3
   329  		case CAN10kBps:
   330  			cfg1 = mcp8mHz10kBpsCfg1
   331  			cfg2 = mcp8mHz10kBpsCfg2
   332  			cfg3 = mcp8mHz10kBpsCfg3
   333  		case CAN20kBps:
   334  			cfg1 = mcp8mHz20kBpsCfg1
   335  			cfg2 = mcp8mHz20kBpsCfg2
   336  			cfg3 = mcp8mHz20kBpsCfg3
   337  		case CAN31k25Bps:
   338  			cfg1 = mcp8mHz31k25BpsCfg1
   339  			cfg2 = mcp8mHz31k25BpsCfg2
   340  			cfg3 = mcp8mHz31k25BpsCfg3
   341  		case CAN40kBps:
   342  			cfg1 = mcp8mHz40kBpsCfg1
   343  			cfg2 = mcp8mHz40kBpsCfg2
   344  			cfg3 = mcp8mHz40kBpsCfg3
   345  		case CAN50kBps:
   346  			cfg1 = mcp8mHz50kBpsCfg1
   347  			cfg2 = mcp8mHz50kBpsCfg2
   348  			cfg3 = mcp8mHz50kBpsCfg3
   349  		case CAN80kBps:
   350  			cfg1 = mcp8mHz80kBpsCfg1
   351  			cfg2 = mcp8mHz80kBpsCfg2
   352  			cfg3 = mcp8mHz80kBpsCfg3
   353  		case CAN100kBps:
   354  			cfg1 = mcp8mHz100kBpsCfg1
   355  			cfg2 = mcp8mHz100kBpsCfg2
   356  			cfg3 = mcp8mHz100kBpsCfg3
   357  		case CAN125kBps:
   358  			cfg1 = mcp8mHz125kBpsCfg1
   359  			cfg2 = mcp8mHz125kBpsCfg2
   360  			cfg3 = mcp8mHz125kBpsCfg3
   361  		case CAN200kBps:
   362  			cfg1 = mcp8mHz200kBpsCfg1
   363  			cfg2 = mcp8mHz200kBpsCfg2
   364  			cfg3 = mcp8mHz200kBpsCfg3
   365  		case CAN250kBps:
   366  			cfg1 = mcp8mHz250kBpsCfg1
   367  			cfg2 = mcp8mHz250kBpsCfg2
   368  			cfg3 = mcp8mHz250kBpsCfg3
   369  		case CAN500kBps:
   370  			cfg1 = mcp8mHz500kBpsCfg1
   371  			cfg2 = mcp8mHz500kBpsCfg2
   372  			cfg3 = mcp8mHz500kBpsCfg3
   373  		case CAN1000kBps:
   374  			cfg1 = mcp8mHz1000kBpsCfg1
   375  			cfg2 = mcp8mHz1000kBpsCfg2
   376  			cfg3 = mcp8mHz1000kBpsCfg3
   377  		default:
   378  			set = false
   379  		}
   380  	default:
   381  		set = false
   382  	}
   383  	if !set {
   384  		return errors.New("invalid parameter")
   385  	}
   386  	if err := d.setRegister(mcpCNF1, cfg1); err != nil {
   387  		return err
   388  	}
   389  	if err := d.setRegister(mcpCNF2, cfg2); err != nil {
   390  		return err
   391  	}
   392  	if err := d.setRegister(mcpCNF3, cfg3); err != nil {
   393  		return err
   394  	}
   395  
   396  	return nil
   397  }
   398  
   399  func (d *Device) initCANBuffers() error {
   400  	a1 := byte(mcpTXB0CTRL)
   401  	a2 := byte(mcpTXB1CTRL)
   402  	a3 := byte(mcpTXB2CTRL)
   403  	for i := 0; i < 14; i++ {
   404  		if err := d.setRegister(a1, 0); err != nil {
   405  			return err
   406  		}
   407  		if err := d.setRegister(a2, 0); err != nil {
   408  			return err
   409  		}
   410  		if err := d.setRegister(a3, 0); err != nil {
   411  			return err
   412  		}
   413  		a1++
   414  		a2++
   415  		a3++
   416  	}
   417  
   418  	if err := d.setRegister(mcpRXB0CTRL, 0); err != nil {
   419  		return err
   420  	}
   421  	if err := d.setRegister(mcpRXB1CTRL, 0); err != nil {
   422  		return err
   423  	}
   424  
   425  	return nil
   426  }
   427  
   428  func (d *Device) readMsg() error {
   429  	status, err := d.readRxTxStatus()
   430  	if err != nil {
   431  		return err
   432  	}
   433  	if (status & mcpRX0IF) == 0x01 {
   434  		err := d.readRxBuffer(mcpReadRx0)
   435  		if err != nil {
   436  			return err
   437  		}
   438  	} else if (status & mcpRX1IF) == 0x02 {
   439  		err := d.readRxBuffer(mcpReadRx1)
   440  		if err != nil {
   441  			return err
   442  		}
   443  	} else {
   444  		return fmt.Errorf("readMsg: nothing is received")
   445  	}
   446  
   447  	return nil
   448  }
   449  
   450  func (d *Device) readRxBuffer(loadAddr uint8) error {
   451  	msg := d.msg
   452  	d.cs.Low()
   453  	defer d.cs.High()
   454  	_, err := d.spi.readWrite(loadAddr)
   455  	if err != nil {
   456  		return err
   457  	}
   458  	err = d.spi.read(4)
   459  	if err != nil {
   460  		return err
   461  	}
   462  	buf := d.spi.rx
   463  	msg.ID = uint32((uint32(buf[0]) << 3) + (uint32(buf[1]) >> 5))
   464  	msg.Ext = false
   465  	if (buf[1] & mcpTxbExideM) == mcpTxbExideM {
   466  		// extended id
   467  		msg.ID = uint32(uint32(msg.ID<<2) + uint32(buf[1]&0x03))
   468  		msg.ID = uint32(uint32(msg.ID<<8) + uint32(buf[2]))
   469  		msg.ID = uint32(uint32(msg.ID<<8) + uint32(buf[3]))
   470  		msg.Ext = true
   471  	}
   472  	err = d.spi.read(1)
   473  	if err != nil {
   474  		return err
   475  	}
   476  	msgSize := d.spi.rx[0]
   477  	msg.Dlc = uint8(msgSize & mcpDlcMask)
   478  	msg.Rtr = false
   479  	if (msgSize & mcpRtrMask) == 0x40 {
   480  		msg.Rtr = true
   481  	}
   482  	readLen := uint8(canMaxCharInMessage)
   483  	if msg.Dlc < canMaxCharInMessage {
   484  		readLen = msg.Dlc
   485  	}
   486  	err = d.spi.read(int(readLen))
   487  	if err != nil {
   488  		return err
   489  	}
   490  	msg.Data = d.spi.rx
   491  
   492  	return err
   493  }
   494  
   495  func (d *Device) getNextFreeTxBuf() (uint8, uint8, error) {
   496  	status, err := d.readStatus()
   497  	if err != nil {
   498  		return 0, mcpAlltxbusy, err
   499  	}
   500  	status &= mcpStatTxPendingMask
   501  
   502  	bufNum := uint8(0x00)
   503  
   504  	if status == mcpStatTxPendingMask {
   505  		return 0, mcpAlltxbusy, nil
   506  	}
   507  
   508  	for i := 0; i < int(mcpNTxbuffers-nReservedTx(0)); i++ {
   509  		if (status & txStatusPendingFlag(uint8(i))) == 0 {
   510  			bufNum = txCtrlReg(uint8(i)) + 1
   511  			d.modifyRegister(mcpCANINTF, txIfFlag(uint8(i)), 0)
   512  			return bufNum, mcp2515Ok, nil
   513  		}
   514  	}
   515  
   516  	return 0, mcpAlltxbusy, nil
   517  }
   518  
   519  func (d *Device) writeCANMsg(bufNum uint8, canid uint32, ext, rtrBit, dlc uint8, data []byte) error {
   520  	d.cs.Low()
   521  	defer d.cs.High()
   522  	_, err := d.spi.readWrite(txSidhToLoad(bufNum))
   523  	if err != nil {
   524  		return err
   525  	}
   526  	err = d.spi.clearBuffer(tx)
   527  	if err != nil {
   528  		return err
   529  	}
   530  	err = d.spi.setTxBufData(canid, ext, rtrBit, dlc, data)
   531  	if err != nil {
   532  		return err
   533  	}
   534  	err = d.spi.write()
   535  	if err != nil {
   536  		return err
   537  	}
   538  	// Since cs.Low and cs.High are executed in d.startTransmission,
   539  	// it is necessary to set cs.High once to separate the instruction of mcp2515.
   540  	d.cs.High()
   541  
   542  	err = d.startTransmission(bufNum)
   543  	if err != nil {
   544  		return err
   545  	}
   546  
   547  	return nil
   548  }
   549  
   550  func (s *SPI) setTxBufData(canid uint32, ext, rtrBit, dlc uint8, data []byte) error {
   551  	canid = canid & 0x0FFFF
   552  	if ext == 1 {
   553  		// TODO: add Extended ID
   554  		err := s.setTxData(0)
   555  		if err != nil {
   556  			return err
   557  		}
   558  		err = s.setTxData(0)
   559  		if err != nil {
   560  			return err
   561  		}
   562  		err = s.setTxData(0)
   563  		if err != nil {
   564  			return err
   565  		}
   566  		err = s.setTxData(0)
   567  		if err != nil {
   568  			return err
   569  		}
   570  	} else {
   571  		err := s.setTxData(byte(canid >> 3))
   572  		if err != nil {
   573  			return err
   574  		}
   575  		err = s.setTxData(byte((canid & 0x07) << 5))
   576  		if err != nil {
   577  			return err
   578  		}
   579  		err = s.setTxData(0)
   580  		if err != nil {
   581  			return err
   582  		}
   583  		err = s.setTxData(0)
   584  		if err != nil {
   585  			return err
   586  		}
   587  	}
   588  	if rtrBit == 1 {
   589  		dlc |= mcpRtrMask
   590  	} else {
   591  		dlc |= (0)
   592  	}
   593  	err := s.setTxData(dlc)
   594  	if err != nil {
   595  		return err
   596  	}
   597  	for _, d := range data {
   598  		err := s.setTxData(d)
   599  		if err != nil {
   600  			return err
   601  		}
   602  	}
   603  
   604  	return nil
   605  }
   606  
   607  func (d *Device) startTransmission(bufNum uint8) error {
   608  	d.cs.Low()
   609  	_, err := d.spi.readWrite(txSidhToRTS(bufNum))
   610  	d.cs.High()
   611  	if err != nil {
   612  		return err
   613  	}
   614  
   615  	return nil
   616  }
   617  
   618  func nReservedTx(number uint8) uint8 {
   619  	if number < mcpNTxbuffers {
   620  		return number
   621  	}
   622  	return mcpNTxbuffers - 1
   623  }
   624  
   625  func txStatusPendingFlag(i uint8) uint8 {
   626  	ret := uint8(0)
   627  	switch i {
   628  	case 0:
   629  		ret = mcpStatTx0Pending
   630  	case 1:
   631  		ret = mcpStatTx1Pending
   632  	case 2:
   633  		ret = mcpStatTx2Pending
   634  	}
   635  	return ret
   636  }
   637  
   638  func txCtrlReg(status uint8) uint8 {
   639  	ret := uint8(0)
   640  	switch status {
   641  	case 0:
   642  		ret = mcpTXB0CTRL
   643  	case 1:
   644  		ret = mcpTXB1CTRL
   645  	case 2:
   646  		ret = mcpTXB2CTRL
   647  	}
   648  	return ret
   649  }
   650  
   651  func txIfFlag(i uint8) uint8 {
   652  	ret := uint8(0)
   653  	switch i {
   654  	case 0:
   655  		ret = mcpTX0IF
   656  	case 1:
   657  		ret = mcpTX1IF
   658  	case 2:
   659  		ret = mcpTX2IF
   660  	}
   661  	return ret
   662  }
   663  
   664  func txSidhToSidh(i uint8) uint8 {
   665  	ret := uint8(0)
   666  	switch i {
   667  	case mcpTX0IF:
   668  		ret = mcpTXB0SIDH
   669  	case mcpTX1IF:
   670  		ret = mcpTXB1SIDH
   671  	case mcpTX2IF:
   672  		ret = mcpTXB2SIDH
   673  	}
   674  	return ret
   675  }
   676  
   677  func txSidhToRTS(i uint8) uint8 {
   678  	ret := uint8(0)
   679  	switch i {
   680  	case mcpTXB0SIDH:
   681  		ret = mcpRtsTx0
   682  	case mcpTXB1SIDH:
   683  		ret = mcpRtsTx1
   684  	case mcpTXB2SIDH:
   685  		ret = mcpRtsTx2
   686  	}
   687  	return ret
   688  }
   689  
   690  func txSidhToLoad(i uint8) uint8 {
   691  	ret := uint8(0)
   692  	switch i {
   693  	case mcpTXB0SIDH:
   694  		ret = mcpLoadTx0
   695  	case mcpTXB1SIDH:
   696  		ret = mcpLoadTx1
   697  	case mcpTXB2SIDH:
   698  		ret = mcpLoadTx2
   699  	}
   700  	return ret
   701  }
   702  
   703  func (d *Device) setRegister(addr, value byte) error {
   704  	d.cs.Low()
   705  	defer d.cs.High()
   706  	_, err := d.spi.readWrite(mcpWrite)
   707  	if err != nil {
   708  		return err
   709  	}
   710  	_, err = d.spi.readWrite(addr)
   711  	if err != nil {
   712  		return err
   713  	}
   714  	_, err = d.spi.readWrite(value)
   715  	if err != nil {
   716  		return err
   717  	}
   718  	// time.Sleep(time.Microsecond * 4)
   719  
   720  	return nil
   721  }
   722  
   723  func (d *Device) readRegister(addr byte) (byte, error) {
   724  	d.cs.Low()
   725  	defer d.cs.High()
   726  	_, err := d.spi.readWrite(mcpRead)
   727  	if err != nil {
   728  		return 0, err
   729  	}
   730  	_, err = d.spi.readWrite(addr)
   731  	if err != nil {
   732  		return 0, err
   733  	}
   734  	err = d.spi.read(1)
   735  	if err != nil {
   736  		return 0, err
   737  	}
   738  	// time.Sleep(time.Microsecond * 4)
   739  	return d.spi.rx[0], nil
   740  }
   741  
   742  func (d *Device) modifyRegister(addr, mask, data byte) error {
   743  	d.cs.Low()
   744  	defer d.cs.High()
   745  	_, err := d.spi.readWrite(mcpBitMod)
   746  	if err != nil {
   747  		return err
   748  	}
   749  	_, err = d.spi.readWrite(addr)
   750  	if err != nil {
   751  		return err
   752  	}
   753  	_, err = d.spi.readWrite(mask)
   754  	if err != nil {
   755  		return err
   756  	}
   757  	_, err = d.spi.readWrite(data)
   758  	if err != nil {
   759  		return err
   760  	}
   761  	// time.Sleep(time.Microsecond * 4)
   762  
   763  	return nil
   764  }
   765  
   766  func (d *Device) requestNewMode(newMode byte) error {
   767  	s := time.Now()
   768  	for {
   769  		err := d.modifyRegister(mcpCANCTRL, modeMask, newMode)
   770  		if err != nil {
   771  			return err
   772  		}
   773  		r, err := d.readRegister(mcpCANSTAT)
   774  		if err != nil {
   775  			return err
   776  		}
   777  		if r&modeMask == newMode {
   778  			return nil
   779  		} else if e := time.Now(); e.Sub(s) > 200*time.Millisecond {
   780  			return errors.New("requestNewMode max time expired")
   781  		}
   782  	}
   783  }
   784  
   785  func (d *Device) readStatus() (byte, error) {
   786  	d.cs.Low()
   787  	defer d.cs.High()
   788  	_, err := d.spi.readWrite(mcpReadStatus)
   789  	if err != nil {
   790  		return 0, err
   791  	}
   792  	err = d.spi.read(1)
   793  	if err != nil {
   794  		return 0, err
   795  	}
   796  
   797  	return d.spi.rx[0], nil
   798  }
   799  
   800  func (d *Device) readRxTxStatus() (byte, error) {
   801  	status, err := d.readStatus()
   802  	if err != nil {
   803  		return 0, err
   804  	}
   805  	ret := status & (mcpStatTxifMask | mcpStatRxifMask)
   806  	if (status & mcpStatTx0if) == 0x08 {
   807  		ret |= mcpTX0IF
   808  	}
   809  	if (status & mcpStatTx1if) == 0x20 {
   810  		ret |= mcpTX1IF
   811  	}
   812  	if (status & mcpStatTx2if) == 0x80 {
   813  		ret |= mcpTX2IF
   814  	}
   815  	ret |= ret & mcpStatRxifMask
   816  
   817  	return ret, nil
   818  }
   819  
   820  type SPI struct {
   821  	bus drivers.SPI
   822  	tx  []byte
   823  	rx  []byte
   824  }
   825  
   826  const (
   827  	tx = iota
   828  	rx
   829  )
   830  
   831  func (s *SPI) readWrite(w byte) (byte, error) {
   832  	return s.bus.Transfer(w)
   833  }
   834  
   835  func (s *SPI) read(readLength int) error {
   836  	err := s.clearBuffer(rx)
   837  	if err != nil {
   838  		return err
   839  	}
   840  	err = s.setBufferLength(readLength, rx)
   841  	if err != nil {
   842  		return err
   843  	}
   844  	return s.bus.Tx(nil, s.rx)
   845  }
   846  
   847  func (s *SPI) write() error {
   848  	return s.bus.Tx(s.tx, nil)
   849  }
   850  
   851  func (s *SPI) clearBuffer(dir int) error { return s.setBufferLength(0, dir) }
   852  
   853  func (s *SPI) setBufferLength(length int, dir int) error {
   854  	if dir == tx {
   855  		if length > cap(s.tx) {
   856  			return fmt.Errorf("length is longer than capacity")
   857  		}
   858  		s.tx = s.tx[:length]
   859  	} else if dir == rx {
   860  		if length > cap(s.rx) {
   861  			return fmt.Errorf("length is longer than capacity")
   862  		}
   863  		s.rx = s.rx[:length]
   864  	} else {
   865  		return fmt.Errorf("invalid direction")
   866  	}
   867  	return nil
   868  }
   869  
   870  func (s *SPI) setTxData(data byte) error {
   871  	if len(s.tx) >= bufferSize {
   872  		return fmt.Errorf("cannot expand buffer (to avoid memory allocation)")
   873  	}
   874  	s.tx = append(s.tx, data)
   875  
   876  	return nil
   877  }
   878  
   879  func (d *Device) dumpMode() error {
   880  	m, err := d.getMode()
   881  	if err != nil {
   882  		return err
   883  	}
   884  	fmt.Printf("Mode: %02X\r\n", m)
   885  
   886  	return nil
   887  }
   888  
   889  func (d *Device) dumpRegister(addr byte) error {
   890  	r, err := d.readRegister(addr)
   891  	if err != nil {
   892  		return err
   893  	}
   894  	fmt.Printf("Register: %02X = %02X\r\n", addr, r)
   895  
   896  	return nil
   897  }