aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLaurent Dufour <ldufour@linux.vnet.ibm.com>2015-07-31 05:29:50 -0400
committerMichael Ellerman <mpe@ellerman.id.au>2015-08-20 04:19:08 -0400
commit480798044eb268a31f6b84bc3b7f99b9989e463d (patch)
tree76eae8f4a721e705dcbf48c52d7c7327454ec3b5
parent84ad6e5cd3e8b365c893f31787864cae5500610b (diff)
powerpc/hvsi: Fix endianness issues in the HVSI driver
This patch fixes several endianness issues detected when running the HVSI driver in little endian mode. These issues are raised in little endian mode because the data exchanged in memory between the kernel and the hypervisor has to be in big endian format. This exhibits as errors such as: irq: (null) didn't like hwirq-0x1000a00 to VIRQ16 mapping (rc=-22) hvsi_console_init: couldn't create irq mapping for 0x1000a00 The data structures already have endian annotations, and sparse is generating numerous warnings based on those. This commit fixes all of them. Signed-off-by: Laurent Dufour <ldufour@linux.vnet.ibm.com> CC: Greg Kroah-Hartman <gregkh@linuxfoundation.org> CC: Jiri Slaby <jslaby@suse.cz> CC: linuxppc-dev@lists.ozlabs.org CC: linux-kernel@vger.kernel.org [mpe: Flesh out change log] Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
-rw-r--r--drivers/tty/hvc/hvsi.c46
1 files changed, 24 insertions, 22 deletions
diff --git a/drivers/tty/hvc/hvsi.c b/drivers/tty/hvc/hvsi.c
index 41901997c0d6..a75146f600cb 100644
--- a/drivers/tty/hvc/hvsi.c
+++ b/drivers/tty/hvc/hvsi.c
@@ -240,9 +240,9 @@ static void hvsi_recv_control(struct hvsi_struct *hp, uint8_t *packet,
240{ 240{
241 struct hvsi_control *header = (struct hvsi_control *)packet; 241 struct hvsi_control *header = (struct hvsi_control *)packet;
242 242
243 switch (header->verb) { 243 switch (be16_to_cpu(header->verb)) {
244 case VSV_MODEM_CTL_UPDATE: 244 case VSV_MODEM_CTL_UPDATE:
245 if ((header->word & HVSI_TSCD) == 0) { 245 if ((be32_to_cpu(header->word) & HVSI_TSCD) == 0) {
246 /* CD went away; no more connection */ 246 /* CD went away; no more connection */
247 pr_debug("hvsi%i: CD dropped\n", hp->index); 247 pr_debug("hvsi%i: CD dropped\n", hp->index);
248 hp->mctrl &= TIOCM_CD; 248 hp->mctrl &= TIOCM_CD;
@@ -267,6 +267,7 @@ static void hvsi_recv_control(struct hvsi_struct *hp, uint8_t *packet,
267static void hvsi_recv_response(struct hvsi_struct *hp, uint8_t *packet) 267static void hvsi_recv_response(struct hvsi_struct *hp, uint8_t *packet)
268{ 268{
269 struct hvsi_query_response *resp = (struct hvsi_query_response *)packet; 269 struct hvsi_query_response *resp = (struct hvsi_query_response *)packet;
270 uint32_t mctrl_word;
270 271
271 switch (hp->state) { 272 switch (hp->state) {
272 case HVSI_WAIT_FOR_VER_RESPONSE: 273 case HVSI_WAIT_FOR_VER_RESPONSE:
@@ -274,9 +275,10 @@ static void hvsi_recv_response(struct hvsi_struct *hp, uint8_t *packet)
274 break; 275 break;
275 case HVSI_WAIT_FOR_MCTRL_RESPONSE: 276 case HVSI_WAIT_FOR_MCTRL_RESPONSE:
276 hp->mctrl = 0; 277 hp->mctrl = 0;
277 if (resp->u.mctrl_word & HVSI_TSDTR) 278 mctrl_word = be32_to_cpu(resp->u.mctrl_word);
279 if (mctrl_word & HVSI_TSDTR)
278 hp->mctrl |= TIOCM_DTR; 280 hp->mctrl |= TIOCM_DTR;
279 if (resp->u.mctrl_word & HVSI_TSCD) 281 if (mctrl_word & HVSI_TSCD)
280 hp->mctrl |= TIOCM_CD; 282 hp->mctrl |= TIOCM_CD;
281 __set_state(hp, HVSI_OPEN); 283 __set_state(hp, HVSI_OPEN);
282 break; 284 break;
@@ -295,10 +297,10 @@ static int hvsi_version_respond(struct hvsi_struct *hp, uint16_t query_seqno)
295 297
296 packet.hdr.type = VS_QUERY_RESPONSE_PACKET_HEADER; 298 packet.hdr.type = VS_QUERY_RESPONSE_PACKET_HEADER;
297 packet.hdr.len = sizeof(struct hvsi_query_response); 299 packet.hdr.len = sizeof(struct hvsi_query_response);
298 packet.hdr.seqno = atomic_inc_return(&hp->seqno); 300 packet.hdr.seqno = cpu_to_be16(atomic_inc_return(&hp->seqno));
299 packet.verb = VSV_SEND_VERSION_NUMBER; 301 packet.verb = cpu_to_be16(VSV_SEND_VERSION_NUMBER);
300 packet.u.version = HVSI_VERSION; 302 packet.u.version = HVSI_VERSION;
301 packet.query_seqno = query_seqno+1; 303 packet.query_seqno = cpu_to_be16(query_seqno+1);
302 304
303 pr_debug("%s: sending %i bytes\n", __func__, packet.hdr.len); 305 pr_debug("%s: sending %i bytes\n", __func__, packet.hdr.len);
304 dbg_dump_hex((uint8_t*)&packet, packet.hdr.len); 306 dbg_dump_hex((uint8_t*)&packet, packet.hdr.len);
@@ -319,7 +321,7 @@ static void hvsi_recv_query(struct hvsi_struct *hp, uint8_t *packet)
319 321
320 switch (hp->state) { 322 switch (hp->state) {
321 case HVSI_WAIT_FOR_VER_QUERY: 323 case HVSI_WAIT_FOR_VER_QUERY:
322 hvsi_version_respond(hp, query->hdr.seqno); 324 hvsi_version_respond(hp, be16_to_cpu(query->hdr.seqno));
323 __set_state(hp, HVSI_OPEN); 325 __set_state(hp, HVSI_OPEN);
324 break; 326 break;
325 default: 327 default:
@@ -555,8 +557,8 @@ static int hvsi_query(struct hvsi_struct *hp, uint16_t verb)
555 557
556 packet.hdr.type = VS_QUERY_PACKET_HEADER; 558 packet.hdr.type = VS_QUERY_PACKET_HEADER;
557 packet.hdr.len = sizeof(struct hvsi_query); 559 packet.hdr.len = sizeof(struct hvsi_query);
558 packet.hdr.seqno = atomic_inc_return(&hp->seqno); 560 packet.hdr.seqno = cpu_to_be16(atomic_inc_return(&hp->seqno));
559 packet.verb = verb; 561 packet.verb = cpu_to_be16(verb);
560 562
561 pr_debug("%s: sending %i bytes\n", __func__, packet.hdr.len); 563 pr_debug("%s: sending %i bytes\n", __func__, packet.hdr.len);
562 dbg_dump_hex((uint8_t*)&packet, packet.hdr.len); 564 dbg_dump_hex((uint8_t*)&packet, packet.hdr.len);
@@ -596,14 +598,14 @@ static int hvsi_set_mctrl(struct hvsi_struct *hp, uint16_t mctrl)
596 struct hvsi_control packet __ALIGNED__; 598 struct hvsi_control packet __ALIGNED__;
597 int wrote; 599 int wrote;
598 600
599 packet.hdr.type = VS_CONTROL_PACKET_HEADER, 601 packet.hdr.type = VS_CONTROL_PACKET_HEADER;
600 packet.hdr.seqno = atomic_inc_return(&hp->seqno); 602 packet.hdr.seqno = cpu_to_be16(atomic_inc_return(&hp->seqno));
601 packet.hdr.len = sizeof(struct hvsi_control); 603 packet.hdr.len = sizeof(struct hvsi_control);
602 packet.verb = VSV_SET_MODEM_CTL; 604 packet.verb = cpu_to_be16(VSV_SET_MODEM_CTL);
603 packet.mask = HVSI_TSDTR; 605 packet.mask = cpu_to_be32(HVSI_TSDTR);
604 606
605 if (mctrl & TIOCM_DTR) 607 if (mctrl & TIOCM_DTR)
606 packet.word = HVSI_TSDTR; 608 packet.word = cpu_to_be32(HVSI_TSDTR);
607 609
608 pr_debug("%s: sending %i bytes\n", __func__, packet.hdr.len); 610 pr_debug("%s: sending %i bytes\n", __func__, packet.hdr.len);
609 dbg_dump_hex((uint8_t*)&packet, packet.hdr.len); 611 dbg_dump_hex((uint8_t*)&packet, packet.hdr.len);
@@ -680,7 +682,7 @@ static int hvsi_put_chars(struct hvsi_struct *hp, const char *buf, int count)
680 BUG_ON(count > HVSI_MAX_OUTGOING_DATA); 682 BUG_ON(count > HVSI_MAX_OUTGOING_DATA);
681 683
682 packet.hdr.type = VS_DATA_PACKET_HEADER; 684 packet.hdr.type = VS_DATA_PACKET_HEADER;
683 packet.hdr.seqno = atomic_inc_return(&hp->seqno); 685 packet.hdr.seqno = cpu_to_be16(atomic_inc_return(&hp->seqno));
684 packet.hdr.len = count + sizeof(struct hvsi_header); 686 packet.hdr.len = count + sizeof(struct hvsi_header);
685 memcpy(&packet.data, buf, count); 687 memcpy(&packet.data, buf, count);
686 688
@@ -697,9 +699,9 @@ static void hvsi_close_protocol(struct hvsi_struct *hp)
697 struct hvsi_control packet __ALIGNED__; 699 struct hvsi_control packet __ALIGNED__;
698 700
699 packet.hdr.type = VS_CONTROL_PACKET_HEADER; 701 packet.hdr.type = VS_CONTROL_PACKET_HEADER;
700 packet.hdr.seqno = atomic_inc_return(&hp->seqno); 702 packet.hdr.seqno = cpu_to_be16(atomic_inc_return(&hp->seqno));
701 packet.hdr.len = 6; 703 packet.hdr.len = 6;
702 packet.verb = VSV_CLOSE_PROTOCOL; 704 packet.verb = cpu_to_be16(VSV_CLOSE_PROTOCOL);
703 705
704 pr_debug("%s: sending %i bytes\n", __func__, packet.hdr.len); 706 pr_debug("%s: sending %i bytes\n", __func__, packet.hdr.len);
705 dbg_dump_hex((uint8_t*)&packet, packet.hdr.len); 707 dbg_dump_hex((uint8_t*)&packet, packet.hdr.len);
@@ -1180,7 +1182,7 @@ static int __init hvsi_console_init(void)
1180 /* search device tree for vty nodes */ 1182 /* search device tree for vty nodes */
1181 for_each_compatible_node(vty, "serial", "hvterm-protocol") { 1183 for_each_compatible_node(vty, "serial", "hvterm-protocol") {
1182 struct hvsi_struct *hp; 1184 struct hvsi_struct *hp;
1183 const uint32_t *vtermno, *irq; 1185 const __be32 *vtermno, *irq;
1184 1186
1185 vtermno = of_get_property(vty, "reg", NULL); 1187 vtermno = of_get_property(vty, "reg", NULL);
1186 irq = of_get_property(vty, "interrupts", NULL); 1188 irq = of_get_property(vty, "interrupts", NULL);
@@ -1202,11 +1204,11 @@ static int __init hvsi_console_init(void)
1202 hp->index = hvsi_count; 1204 hp->index = hvsi_count;
1203 hp->inbuf_end = hp->inbuf; 1205 hp->inbuf_end = hp->inbuf;
1204 hp->state = HVSI_CLOSED; 1206 hp->state = HVSI_CLOSED;
1205 hp->vtermno = *vtermno; 1207 hp->vtermno = be32_to_cpup(vtermno);
1206 hp->virq = irq_create_mapping(NULL, irq[0]); 1208 hp->virq = irq_create_mapping(NULL, be32_to_cpup(irq));
1207 if (hp->virq == 0) { 1209 if (hp->virq == 0) {
1208 printk(KERN_ERR "%s: couldn't create irq mapping for 0x%x\n", 1210 printk(KERN_ERR "%s: couldn't create irq mapping for 0x%x\n",
1209 __func__, irq[0]); 1211 __func__, be32_to_cpup(irq));
1210 tty_port_destroy(&hp->port); 1212 tty_port_destroy(&hp->port);
1211 continue; 1213 continue;
1212 } 1214 }