aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/usb/gadget/file_storage.c129
-rw-r--r--drivers/usb/gadget/storage_common.c116
2 files changed, 128 insertions, 117 deletions
diff --git a/drivers/usb/gadget/file_storage.c b/drivers/usb/gadget/file_storage.c
index ee712a5715e7..7998402b1840 100644
--- a/drivers/usb/gadget/file_storage.c
+++ b/drivers/usb/gadget/file_storage.c
@@ -278,18 +278,14 @@ static char fsg_string_serial[13];
278static const char fsg_string_config[] = "Self-powered"; 278static const char fsg_string_config[] = "Self-powered";
279static const char fsg_string_interface[] = "Mass Storage"; 279static const char fsg_string_interface[] = "Mass Storage";
280 280
281
282#include "storage_common.c"
283
284
281MODULE_DESCRIPTION(DRIVER_DESC); 285MODULE_DESCRIPTION(DRIVER_DESC);
282MODULE_AUTHOR("Alan Stern"); 286MODULE_AUTHOR("Alan Stern");
283MODULE_LICENSE("Dual BSD/GPL"); 287MODULE_LICENSE("Dual BSD/GPL");
284 288
285/* Thanks to NetChip Technologies for donating this product ID.
286 *
287 * DO NOT REUSE THESE IDs with any other driver!! Ever!!
288 * Instead: allocate your own, using normal USB-IF procedures. */
289#define FSG_VENDOR_ID 0x0525 // NetChip
290#define FSG_PRODUCT_ID 0xa4a5 // Linux-USB File-backed Storage Gadget
291
292
293/* 289/*
294 * This driver assumes self-powered hardware and has no way for users to 290 * This driver assumes self-powered hardware and has no way for users to
295 * trigger remote wakeup. It uses autoconfiguration to select endpoints 291 * trigger remote wakeup. It uses autoconfiguration to select endpoints
@@ -302,8 +298,6 @@ MODULE_LICENSE("Dual BSD/GPL");
302 298
303/* Encapsulate the module parameter settings */ 299/* Encapsulate the module parameter settings */
304 300
305#define FSG_MAX_LUNS 8
306
307static struct { 301static struct {
308 char *file[FSG_MAX_LUNS]; 302 char *file[FSG_MAX_LUNS];
309 int ro[FSG_MAX_LUNS]; 303 int ro[FSG_MAX_LUNS];
@@ -410,10 +404,6 @@ MODULE_PARM_DESC(buflen, "I/O buffer size");
410 404
411/*-------------------------------------------------------------------------*/ 405/*-------------------------------------------------------------------------*/
412 406
413#include "storage_common.c"
414
415/*-------------------------------------------------------------------------*/
416
417 407
418struct fsg_dev { 408struct fsg_dev {
419 /* lock protects: state, all the req_busy's, and cbbuf_cmnd */ 409 /* lock protects: state, all the req_busy's, and cbbuf_cmnd */
@@ -3134,107 +3124,10 @@ static int fsg_main_thread(void *fsg_)
3134 3124
3135/*-------------------------------------------------------------------------*/ 3125/*-------------------------------------------------------------------------*/
3136 3126
3137static ssize_t show_ro(struct device *dev, struct device_attribute *attr, char *buf)
3138{
3139 struct fsg_lun *curlun = fsg_lun_from_dev(dev);
3140
3141 return sprintf(buf, "%d\n", fsg_lun_is_open(curlun)
3142 ? curlun->ro
3143 : curlun->initially_ro);
3144}
3145
3146static ssize_t show_file(struct device *dev, struct device_attribute *attr,
3147 char *buf)
3148{
3149 struct fsg_lun *curlun = fsg_lun_from_dev(dev);
3150 struct fsg_dev *fsg = dev_get_drvdata(dev);
3151 char *p;
3152 ssize_t rc;
3153
3154 down_read(&fsg->filesem);
3155 if (fsg_lun_is_open(curlun)) { // Get the complete pathname
3156 p = d_path(&curlun->filp->f_path, buf, PAGE_SIZE - 1);
3157 if (IS_ERR(p))
3158 rc = PTR_ERR(p);
3159 else {
3160 rc = strlen(p);
3161 memmove(buf, p, rc);
3162 buf[rc] = '\n'; // Add a newline
3163 buf[++rc] = 0;
3164 }
3165 } else { // No file, return 0 bytes
3166 *buf = 0;
3167 rc = 0;
3168 }
3169 up_read(&fsg->filesem);
3170 return rc;
3171}
3172
3173
3174static ssize_t store_ro(struct device *dev, struct device_attribute *attr,
3175 const char *buf, size_t count)
3176{
3177 ssize_t rc = count;
3178 struct fsg_lun *curlun = fsg_lun_from_dev(dev);
3179 struct fsg_dev *fsg = dev_get_drvdata(dev);
3180 int i;
3181
3182 if (sscanf(buf, "%d", &i) != 1)
3183 return -EINVAL;
3184
3185 /* Allow the write-enable status to change only while the backing file
3186 * is closed. */
3187 down_read(&fsg->filesem);
3188 if (fsg_lun_is_open(curlun)) {
3189 LDBG(curlun, "read-only status change prevented\n");
3190 rc = -EBUSY;
3191 } else {
3192 curlun->ro = !!i;
3193 curlun->initially_ro = !!i;
3194 LDBG(curlun, "read-only status set to %d\n", curlun->ro);
3195 }
3196 up_read(&fsg->filesem);
3197 return rc;
3198}
3199
3200static ssize_t store_file(struct device *dev, struct device_attribute *attr,
3201 const char *buf, size_t count)
3202{
3203 struct fsg_lun *curlun = fsg_lun_from_dev(dev);
3204 struct fsg_dev *fsg = dev_get_drvdata(dev);
3205 int rc = 0;
3206
3207 if (curlun->prevent_medium_removal && fsg_lun_is_open(curlun)) {
3208 LDBG(curlun, "eject attempt prevented\n");
3209 return -EBUSY; // "Door is locked"
3210 }
3211
3212 /* Remove a trailing newline */
3213 if (count > 0 && buf[count-1] == '\n')
3214 ((char *) buf)[count-1] = 0; // Ugh!
3215
3216 /* Eject current medium */
3217 down_write(&fsg->filesem);
3218 if (fsg_lun_is_open(curlun)) {
3219 fsg_lun_close(curlun);
3220 curlun->unit_attention_data = SS_MEDIUM_NOT_PRESENT;
3221 }
3222
3223 /* Load new medium */
3224 if (count > 0 && buf[0]) {
3225 rc = fsg_lun_open(curlun, buf);
3226 if (rc == 0)
3227 curlun->unit_attention_data =
3228 SS_NOT_READY_TO_READY_TRANSITION;
3229 }
3230 up_write(&fsg->filesem);
3231 return (rc < 0 ? rc : count);
3232}
3233
3234 3127
3235/* The write permissions and store_xxx pointers are set in fsg_bind() */ 3128/* The write permissions and store_xxx pointers are set in fsg_bind() */
3236static DEVICE_ATTR(ro, 0444, show_ro, NULL); 3129static DEVICE_ATTR(ro, 0444, fsg_show_ro, NULL);
3237static DEVICE_ATTR(file, 0444, show_file, NULL); 3130static DEVICE_ATTR(file, 0444, fsg_show_file, NULL);
3238 3131
3239 3132
3240/*-------------------------------------------------------------------------*/ 3133/*-------------------------------------------------------------------------*/
@@ -3249,7 +3142,9 @@ static void fsg_release(struct kref *ref)
3249 3142
3250static void lun_release(struct device *dev) 3143static void lun_release(struct device *dev)
3251{ 3144{
3252 struct fsg_dev *fsg = dev_get_drvdata(dev); 3145 struct rw_semaphore *filesem = dev_get_drvdata(dev);
3146 struct fsg_dev *fsg =
3147 container_of(filesem, struct fsg_dev, filesem);
3253 3148
3254 kref_put(&fsg->ref, fsg_release); 3149 kref_put(&fsg->ref, fsg_release);
3255} 3150}
@@ -3408,10 +3303,10 @@ static int __init fsg_bind(struct usb_gadget *gadget)
3408 3303
3409 if (mod_data.removable) { // Enable the store_xxx attributes 3304 if (mod_data.removable) { // Enable the store_xxx attributes
3410 dev_attr_file.attr.mode = 0644; 3305 dev_attr_file.attr.mode = 0644;
3411 dev_attr_file.store = store_file; 3306 dev_attr_file.store = fsg_store_file;
3412 if (!mod_data.cdrom) { 3307 if (!mod_data.cdrom) {
3413 dev_attr_ro.attr.mode = 0644; 3308 dev_attr_ro.attr.mode = 0644;
3414 dev_attr_ro.store = store_ro; 3309 dev_attr_ro.store = fsg_store_ro;
3415 } 3310 }