50 uint8_t type, /**< mailbox protocol */ |
50 uint8_t type, /**< mailbox protocol */ |
51 size_t size /**< size of the data */ |
51 size_t size /**< size of the data */ |
52 ) |
52 ) |
53 { |
53 { |
54 size_t total_size; |
54 size_t total_size; |
|
55 uint16_t mailbox_offset, mailbox_size; |
55 |
56 |
56 if (unlikely(!slave->sii.mailbox_protocols)) { |
57 if (unlikely(!slave->sii.mailbox_protocols)) { |
57 EC_ERR("Slave %u does not support mailbox communication!\n", |
58 EC_ERR("Slave %u does not support mailbox communication!\n", |
58 slave->ring_position); |
59 slave->ring_position); |
59 return NULL; |
60 return NULL; |
60 } |
61 } |
61 |
62 |
62 total_size = size + 6; |
63 total_size = size + 6; |
63 if (unlikely(total_size > slave->sii.rx_mailbox_size)) { |
64 |
|
65 if (slave->current_state != EC_SLAVE_STATE_BOOT) { |
|
66 mailbox_offset = slave->sii.std_rx_mailbox_offset; |
|
67 mailbox_size = slave->sii.std_rx_mailbox_size; |
|
68 } else { |
|
69 mailbox_offset = slave->sii.boot_rx_mailbox_offset; |
|
70 mailbox_size = slave->sii.boot_rx_mailbox_size; |
|
71 } |
|
72 |
|
73 if (unlikely(total_size > mailbox_size)) { |
64 EC_ERR("Data size does not fit in mailbox!\n"); |
74 EC_ERR("Data size does not fit in mailbox!\n"); |
65 return NULL; |
75 return NULL; |
66 } |
76 } |
67 |
77 |
68 if (ec_datagram_fpwr(datagram, slave->station_address, |
78 if (ec_datagram_fpwr(datagram, slave->station_address, |
69 slave->sii.rx_mailbox_offset, |
79 mailbox_offset, mailbox_size)) |
70 slave->sii.rx_mailbox_size)) |
|
71 return NULL; |
80 return NULL; |
72 |
81 |
73 EC_WRITE_U16(datagram->data, size); // mailbox service data length |
82 EC_WRITE_U16(datagram->data, size); // mailbox service data length |
74 EC_WRITE_U16(datagram->data + 2, slave->station_address); // station addr. |
83 EC_WRITE_U16(datagram->data + 2, slave->station_address); // station addr. |
75 EC_WRITE_U8 (datagram->data + 4, 0x00); // channel & priority |
84 EC_WRITE_U8 (datagram->data + 4, 0x00); // channel & priority |
117 |
126 |
118 int ec_slave_mbox_prepare_fetch(const ec_slave_t *slave, /**< slave */ |
127 int ec_slave_mbox_prepare_fetch(const ec_slave_t *slave, /**< slave */ |
119 ec_datagram_t *datagram /**< datagram */ |
128 ec_datagram_t *datagram /**< datagram */ |
120 ) |
129 ) |
121 { |
130 { |
|
131 uint16_t mailbox_offset, mailbox_size; |
|
132 |
|
133 if (slave->current_state != EC_SLAVE_STATE_BOOT) { |
|
134 mailbox_offset = slave->sii.std_tx_mailbox_offset; |
|
135 mailbox_size = slave->sii.std_tx_mailbox_size; |
|
136 } else { |
|
137 mailbox_offset = slave->sii.boot_tx_mailbox_offset; |
|
138 mailbox_size = slave->sii.boot_tx_mailbox_size; |
|
139 } |
|
140 |
122 if (ec_datagram_fprd(datagram, slave->station_address, |
141 if (ec_datagram_fprd(datagram, slave->station_address, |
123 slave->sii.tx_mailbox_offset, |
142 mailbox_offset, mailbox_size)) |
124 slave->sii.tx_mailbox_size)) return -1; |
143 return -1; |
|
144 |
125 return 0; |
145 return 0; |
126 } |
146 } |
127 |
147 |
128 /*****************************************************************************/ |
148 /*****************************************************************************/ |
129 |
149 |
155 uint8_t *type, /**< expected mailbox protocol */ |
175 uint8_t *type, /**< expected mailbox protocol */ |
156 size_t *size /**< size of the received data */ |
176 size_t *size /**< size of the received data */ |
157 ) |
177 ) |
158 { |
178 { |
159 size_t data_size; |
179 size_t data_size; |
|
180 uint16_t mailbox_offset, mailbox_size; |
|
181 |
|
182 if (slave->current_state != EC_SLAVE_STATE_BOOT) { |
|
183 mailbox_offset = slave->sii.std_tx_mailbox_offset; |
|
184 mailbox_size = slave->sii.std_tx_mailbox_size; |
|
185 } else { |
|
186 mailbox_offset = slave->sii.boot_tx_mailbox_offset; |
|
187 mailbox_size = slave->sii.boot_tx_mailbox_size; |
|
188 } |
160 |
189 |
161 data_size = EC_READ_U16(datagram->data); |
190 data_size = EC_READ_U16(datagram->data); |
162 |
191 |
163 if (data_size > slave->sii.tx_mailbox_size - 6) { |
192 if (data_size > mailbox_size - 6) { |
164 EC_ERR("Corrupt mailbox response received from slave %u!\n", |
193 EC_ERR("Corrupt mailbox response received from slave %u!\n", |
165 slave->ring_position); |
194 slave->ring_position); |
166 ec_print_data(datagram->data, slave->sii.tx_mailbox_size); |
195 ec_print_data(datagram->data, mailbox_size); |
167 return NULL; |
196 return NULL; |
168 } |
197 } |
169 |
198 |
170 *type = EC_READ_U8(datagram->data + 5) & 0x0F; |
199 *type = EC_READ_U8(datagram->data + 5) & 0x0F; |
171 *size = data_size; |
200 *size = data_size; |
172 |
201 |
173 if (*type == 0x00) { |
202 if (*type == 0x00) { |
174 const ec_code_msg_t *mbox_msg; |
203 const ec_code_msg_t *mbox_msg; |
175 uint16_t code = EC_READ_U16(datagram->data + 8); |
204 uint16_t code = EC_READ_U16(datagram->data + 8); |
176 |
205 |
177 EC_ERR("Mailbox error response received from slave %u - ", |
206 EC_ERR("Mailbox error response received from slave %u - ", |
178 slave->ring_position); |
207 slave->ring_position); |
179 |
208 |
180 for (mbox_msg = mbox_error_messages; mbox_msg->code; mbox_msg++) { |
209 for (mbox_msg = mbox_error_messages; mbox_msg->code; mbox_msg++) { |
181 if (mbox_msg->code != code) continue; |
210 if (mbox_msg->code != code) |
|
211 continue; |
182 printk("Code 0x%04X: \"%s\".\n", |
212 printk("Code 0x%04X: \"%s\".\n", |
183 mbox_msg->code, mbox_msg->message); |
213 mbox_msg->code, mbox_msg->message); |
184 break; |
214 break; |
185 } |
215 } |
186 |
216 |
187 if (!mbox_msg->code) |
217 if (!mbox_msg->code) |
188 printk("Unknown error reply code 0x%04X.\n", code); |
218 printk("Unknown error reply code 0x%04X.\n", code); |