diff options
author | Wei Yongjun <yjwei@cn.fujitsu.com> | 2008-09-30 08:32:24 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2008-09-30 08:32:24 -0400 |
commit | ba0166708ef4da7eeb61dd92bbba4d5a749d6561 (patch) | |
tree | 0e28c1d17b67d24125df4f05cbcca94c7e90ccd3 /net/sctp/sm_make_chunk.c | |
parent | 8b122efd13a227d35d5ca242561770db1b5e3658 (diff) |
sctp: Fix kernel panic while process protocol violation parameter
Since call to function sctp_sf_abort_violation() need paramter 'arg' with
'struct sctp_chunk' type, it will read the chunk type and chunk length from
the chunk_hdr member of chunk. But call to sctp_sf_violation_paramlen()
always with 'struct sctp_paramhdr' type's parameter, it will be passed to
sctp_sf_abort_violation(). This may cause kernel panic.
sctp_sf_violation_paramlen()
|-- sctp_sf_abort_violation()
|-- sctp_make_abort_violation()
This patch fixed this problem. This patch also fix two place which called
sctp_sf_violation_paramlen() with wrong paramter type.
Signed-off-by: Wei Yongjun <yjwei@cn.fujitsu.com>
Signed-off-by: Vlad Yasevich <vladislav.yasevich@hp.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/sctp/sm_make_chunk.c')
-rw-r--r-- | net/sctp/sm_make_chunk.c | 37 |
1 files changed, 24 insertions, 13 deletions
diff --git a/net/sctp/sm_make_chunk.c b/net/sctp/sm_make_chunk.c index b599cbba4fbe..d68869f966c3 100644 --- a/net/sctp/sm_make_chunk.c +++ b/net/sctp/sm_make_chunk.c | |||
@@ -1012,6 +1012,29 @@ end: | |||
1012 | return retval; | 1012 | return retval; |
1013 | } | 1013 | } |
1014 | 1014 | ||
1015 | struct sctp_chunk *sctp_make_violation_paramlen( | ||
1016 | const struct sctp_association *asoc, | ||
1017 | const struct sctp_chunk *chunk, | ||
1018 | struct sctp_paramhdr *param) | ||
1019 | { | ||
1020 | struct sctp_chunk *retval; | ||
1021 | static const char error[] = "The following parameter had invalid length:"; | ||
1022 | size_t payload_len = sizeof(error) + sizeof(sctp_errhdr_t) + | ||
1023 | sizeof(sctp_paramhdr_t); | ||
1024 | |||
1025 | retval = sctp_make_abort(asoc, chunk, payload_len); | ||
1026 | if (!retval) | ||
1027 | goto nodata; | ||
1028 | |||
1029 | sctp_init_cause(retval, SCTP_ERROR_PROTO_VIOLATION, | ||
1030 | sizeof(error) + sizeof(sctp_paramhdr_t)); | ||
1031 | sctp_addto_chunk(retval, sizeof(error), error); | ||
1032 | sctp_addto_param(retval, sizeof(sctp_paramhdr_t), param); | ||
1033 | |||
1034 | nodata: | ||
1035 | return retval; | ||
1036 | } | ||
1037 | |||
1015 | /* Make a HEARTBEAT chunk. */ | 1038 | /* Make a HEARTBEAT chunk. */ |
1016 | struct sctp_chunk *sctp_make_heartbeat(const struct sctp_association *asoc, | 1039 | struct sctp_chunk *sctp_make_heartbeat(const struct sctp_association *asoc, |
1017 | const struct sctp_transport *transport, | 1040 | const struct sctp_transport *transport, |
@@ -1782,11 +1805,6 @@ static int sctp_process_inv_paramlength(const struct sctp_association *asoc, | |||
1782 | const struct sctp_chunk *chunk, | 1805 | const struct sctp_chunk *chunk, |
1783 | struct sctp_chunk **errp) | 1806 | struct sctp_chunk **errp) |
1784 | { | 1807 | { |
1785 | static const char error[] = "The following parameter had invalid length:"; | ||
1786 | size_t payload_len = WORD_ROUND(sizeof(error)) + | ||
1787 | sizeof(sctp_paramhdr_t); | ||
1788 | |||
1789 | |||
1790 | /* This is a fatal error. Any accumulated non-fatal errors are | 1808 | /* This is a fatal error. Any accumulated non-fatal errors are |
1791 | * not reported. | 1809 | * not reported. |
1792 | */ | 1810 | */ |
@@ -1794,14 +1812,7 @@ static int sctp_process_inv_paramlength(const struct sctp_association *asoc, | |||
1794 | sctp_chunk_free(*errp); | 1812 | sctp_chunk_free(*errp); |
1795 | 1813 | ||
1796 | /* Create an error chunk and fill it in with our payload. */ | 1814 | /* Create an error chunk and fill it in with our payload. */ |
1797 | *errp = sctp_make_op_error_space(asoc, chunk, payload_len); | 1815 | *errp = sctp_make_violation_paramlen(asoc, chunk, param); |
1798 | |||
1799 | if (*errp) { | ||
1800 | sctp_init_cause(*errp, SCTP_ERROR_PROTO_VIOLATION, | ||
1801 | sizeof(error) + sizeof(sctp_paramhdr_t)); | ||
1802 | sctp_addto_chunk(*errp, sizeof(error), error); | ||
1803 | sctp_addto_param(*errp, sizeof(sctp_paramhdr_t), param); | ||
1804 | } | ||
1805 | 1816 | ||
1806 | return 0; | 1817 | return 0; |
1807 | } | 1818 | } |