diff options
author | Sebastian Ott <sebott@linux.vnet.ibm.com> | 2013-06-25 09:37:44 -0400 |
---|---|---|
committer | Martin Schwidefsky <schwidefsky@de.ibm.com> | 2013-06-26 15:10:31 -0400 |
commit | 2ab14619249cff5835aa66f2c06bfbb0204a30bf (patch) | |
tree | bd2dcc00311a63ada1e1f59a67c00221d3b704a7 | |
parent | a94f0fb1a256455489d475f21c1f902a9280bf9a (diff) |
s390/appldata_net_sum: do not use static data
Using static data for fields which are accessed by HW will fail if
the driver is build as a module (since this would be vmalloc'ed
memory). This Bug was revealed via
"s390: remove virt_to_phys implementation" - the old virt_to_phys
implementation would have translated the address but it was not
guaranteed that the memory was contiguous.
Signed-off-by: Sebastian Ott <sebott@linux.vnet.ibm.com>
Reviewed-by: Gerald Schaefer <gerald.schaefer@de.ibm.com>
Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
-rw-r--r-- | arch/s390/appldata/appldata_net_sum.c | 18 |
1 files changed, 14 insertions, 4 deletions
diff --git a/arch/s390/appldata/appldata_net_sum.c b/arch/s390/appldata/appldata_net_sum.c index 2d224b945355..66037d2622b4 100644 --- a/arch/s390/appldata/appldata_net_sum.c +++ b/arch/s390/appldata/appldata_net_sum.c | |||
@@ -29,7 +29,7 @@ | |||
29 | * book: | 29 | * book: |
30 | * http://oss.software.ibm.com/developerworks/opensource/linux390/index.shtml | 30 | * http://oss.software.ibm.com/developerworks/opensource/linux390/index.shtml |
31 | */ | 31 | */ |
32 | static struct appldata_net_sum_data { | 32 | struct appldata_net_sum_data { |
33 | u64 timestamp; | 33 | u64 timestamp; |
34 | u32 sync_count_1; /* after VM collected the record data, */ | 34 | u32 sync_count_1; /* after VM collected the record data, */ |
35 | u32 sync_count_2; /* sync_count_1 and sync_count_2 should be the | 35 | u32 sync_count_2; /* sync_count_1 and sync_count_2 should be the |
@@ -51,7 +51,7 @@ static struct appldata_net_sum_data { | |||
51 | u64 rx_dropped; /* no space in linux buffers */ | 51 | u64 rx_dropped; /* no space in linux buffers */ |
52 | u64 tx_dropped; /* no space available in linux */ | 52 | u64 tx_dropped; /* no space available in linux */ |
53 | u64 collisions; /* collisions while transmitting */ | 53 | u64 collisions; /* collisions while transmitting */ |
54 | } __attribute__((packed)) appldata_net_sum_data; | 54 | } __packed; |
55 | 55 | ||
56 | 56 | ||
57 | /* | 57 | /* |
@@ -121,7 +121,6 @@ static struct appldata_ops ops = { | |||
121 | .record_nr = APPLDATA_RECORD_NET_SUM_ID, | 121 | .record_nr = APPLDATA_RECORD_NET_SUM_ID, |
122 | .size = sizeof(struct appldata_net_sum_data), | 122 | .size = sizeof(struct appldata_net_sum_data), |
123 | .callback = &appldata_get_net_sum_data, | 123 | .callback = &appldata_get_net_sum_data, |
124 | .data = &appldata_net_sum_data, | ||
125 | .owner = THIS_MODULE, | 124 | .owner = THIS_MODULE, |
126 | .mod_lvl = {0xF0, 0xF0}, /* EBCDIC "00" */ | 125 | .mod_lvl = {0xF0, 0xF0}, /* EBCDIC "00" */ |
127 | }; | 126 | }; |
@@ -134,7 +133,17 @@ static struct appldata_ops ops = { | |||
134 | */ | 133 | */ |
135 | static int __init appldata_net_init(void) | 134 | static int __init appldata_net_init(void) |
136 | { | 135 | { |
137 | return appldata_register_ops(&ops); | 136 | int ret; |
137 | |||
138 | ops.data = kzalloc(sizeof(struct appldata_net_sum_data), GFP_KERNEL); | ||
139 | if (!ops.data) | ||
140 | return -ENOMEM; | ||
141 | |||
142 | ret = appldata_register_ops(&ops); | ||
143 | if (ret) | ||
144 | kfree(ops.data); | ||
145 | |||
146 | return ret; | ||
138 | } | 147 | } |
139 | 148 | ||
140 | /* | 149 | /* |
@@ -145,6 +154,7 @@ static int __init appldata_net_init(void) | |||
145 | static void __exit appldata_net_exit(void) | 154 | static void __exit appldata_net_exit(void) |
146 | { | 155 | { |
147 | appldata_unregister_ops(&ops); | 156 | appldata_unregister_ops(&ops); |
157 | kfree(ops.data); | ||
148 | } | 158 | } |
149 | 159 | ||
150 | 160 | ||