1313#include <linux/err.h>
1414#include <linux/io.h>
1515#include <linux/kernel.h>
16+ #include <linux/memory/ti-aemif.h>
1617#include <linux/module.h>
18+ #include <linux/mutex.h>
1719#include <linux/of.h>
1820#include <linux/of_platform.h>
1921#include <linux/platform_device.h>
7981
8082#define CONFIG_MASK (EW(EW_MAX) | SSTROBE(SSTROBE_MAX) | ASIZE_MAX)
8183
82- /**
83- * struct aemif_cs_timings: structure to hold CS timings
84- * @wstrobe: write strobe width, number of cycles - 1
85- * @rstrobe: read strobe width, number of cycles - 1
86- * @wsetup: write setup width, number of cycles - 1
87- * @whold: write hold width, number of cycles - 1
88- * @rsetup: read setup width, number of cycles - 1
89- * @rhold: read hold width, number of cycles - 1
90- * @ta: minimum turn around time, number of cycles - 1
91- */
92- struct aemif_cs_timings {
93- u32 wstrobe ;
94- u32 rstrobe ;
95- u32 wsetup ;
96- u32 whold ;
97- u32 rsetup ;
98- u32 rhold ;
99- u32 ta ;
100- };
101-
10284/**
10385 * struct aemif_cs_data: structure to hold CS parameters
10486 * @timings: timings configuration
@@ -123,6 +105,7 @@ struct aemif_cs_data {
123105 * @num_cs: number of assigned chip-selects
124106 * @cs_offset: start number of cs nodes
125107 * @cs_data: array of chip-select settings
108+ * @config_cs_lock: lock used to access CS configuration
126109 */
127110struct aemif_device {
128111 void __iomem * base ;
@@ -131,6 +114,7 @@ struct aemif_device {
131114 u8 num_cs ;
132115 int cs_offset ;
133116 struct aemif_cs_data cs_data [NUM_CS ];
117+ struct mutex config_cs_lock ;
134118};
135119
136120/**
@@ -139,7 +123,7 @@ struct aemif_device {
139123 *
140124 * @return: 0 if the timing configuration is valid, negative error number otherwise.
141125 */
142- static int aemif_check_cs_timings (struct aemif_cs_timings * timings )
126+ int aemif_check_cs_timings (struct aemif_cs_timings * timings )
143127{
144128 if (timings -> ta > TA_MAX )
145129 return - EINVAL ;
@@ -164,6 +148,7 @@ static int aemif_check_cs_timings(struct aemif_cs_timings *timings)
164148
165149 return 0 ;
166150}
151+ EXPORT_SYMBOL_GPL (aemif_check_cs_timings );
167152
168153/**
169154 * aemif_set_cs_timings() - Set the timing configuration of a given chip select.
@@ -173,7 +158,8 @@ static int aemif_check_cs_timings(struct aemif_cs_timings *timings)
173158 *
174159 * @return: 0 on success, else negative errno.
175160 */
176- static int aemif_set_cs_timings (struct aemif_device * aemif , u8 cs , struct aemif_cs_timings * timings )
161+ int aemif_set_cs_timings (struct aemif_device * aemif , u8 cs ,
162+ struct aemif_cs_timings * timings )
177163{
178164 unsigned int offset ;
179165 u32 val , set ;
@@ -195,13 +181,16 @@ static int aemif_set_cs_timings(struct aemif_device *aemif, u8 cs, struct aemif_
195181
196182 offset = A1CR_OFFSET + cs * 4 ;
197183
184+ mutex_lock (& aemif -> config_cs_lock );
198185 val = readl (aemif -> base + offset );
199186 val &= ~TIMINGS_MASK ;
200187 val |= set ;
201188 writel (val , aemif -> base + offset );
189+ mutex_unlock (& aemif -> config_cs_lock );
202190
203191 return 0 ;
204192}
193+ EXPORT_SYMBOL_GPL (aemif_set_cs_timings );
205194
206195/**
207196 * aemif_calc_rate - calculate timing data.
@@ -257,10 +246,12 @@ static int aemif_config_abus(struct platform_device *pdev, int csnum)
257246 if (data -> enable_ss )
258247 set |= ACR_SSTROBE_MASK ;
259248
249+ mutex_lock (& aemif -> config_cs_lock );
260250 val = readl (aemif -> base + offset );
261251 val &= ~CONFIG_MASK ;
262252 val |= set ;
263253 writel (val , aemif -> base + offset );
254+ mutex_unlock (& aemif -> config_cs_lock );
264255
265256 return aemif_set_cs_timings (aemif , data -> cs - aemif -> cs_offset , & data -> timings );
266257}
@@ -399,6 +390,7 @@ static int aemif_probe(struct platform_device *pdev)
399390 if (IS_ERR (aemif -> base ))
400391 return PTR_ERR (aemif -> base );
401392
393+ mutex_init (& aemif -> config_cs_lock );
402394 if (np ) {
403395 /*
404396 * For every controller device node, there is a cs device node
0 commit comments