修改文件:

packages/apps/Bluetooth/src/com/android/bluetooth/opp/BluetoothOppReceiveFileInfo.java

相关代码片段:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
public static BluetoothOppReceiveFileInfo generateFileInfo(Context context, int id) {
 
    ContentResolver contentResolver = context.getContentResolver();
    Uri contentUri = Uri.parse(BluetoothShare.CONTENT_URI + "/" + id);
    String filename = null, hint = null, mimeType = null;
    long length = 0;
    Cursor metadataCursor = null;
    try {
        metadataCursor = contentResolver.query(contentUri, new String[] {
            BluetoothShare.FILENAME_HINT, BluetoothShare.TOTAL_BYTES, BluetoothShare.MIMETYPE
            }, null, null, null);
    } catch (SQLiteException e) {
        if (metadataCursor != null) {
            metadataCursor.close();
        }
        metadataCursor = null;
        Log.e(Constants.TAG, "generateFileInfo: " + e);
    } catch (CursorWindowAllocationException e) {
        metadataCursor = null;
        Log.e(Constants.TAG, "generateFileInfo: " + e);
    }
 
    if (metadataCursor != null) {
        try {
            if (metadataCursor.moveToFirst()) {
                hint = metadataCursor.getString(0);
                length = metadataCursor.getLong(1);
                mimeType = metadataCursor.getString(2);
            }
        } finally {
            metadataCursor.close();
            if (V) Log.v(Constants.TAG, "Freeing cursor: " + metadataCursor);
            metadataCursor = null;
        }
    }
 
    File base = null;
    StatFs stat = null;
 
    if (Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) {
        String root = Environment.getExternalStorageDirectory().getPath();
        base = new File(root + Constants.DEFAULT_STORE_SUBDIR);
        if (!base.isDirectory() && !base.mkdir()) {
            if (D) Log.d(Constants.TAG, "Receive File aborted - can't create base directory "
                        + base.getPath());
            return new BluetoothOppReceiveFileInfo(BluetoothShare.STATUS_FILE_ERROR);
        }
        stat = new StatFs(base.getPath());
    } else {
        if (D) Log.d(Constants.TAG, "Receive File aborted - no external storage");
        return new BluetoothOppReceiveFileInfo(BluetoothShare.STATUS_ERROR_NO_SDCARD);
    }
 
    /*
     * Check whether there's enough space on the target filesystem to save
     * the file. Put a bit of margin (in case creating the file grows the
     * system by a few blocks).
     */
    if (stat.getBlockSize() * ((long)stat.getAvailableBlocks() - 4) < length) {
        if (D) Log.d(Constants.TAG, "Receive File aborted - not enough free space");
        return new BluetoothOppReceiveFileInfo(BluetoothShare.STATUS_ERROR_SDCARD_FULL);
    }
 
    filename = choosefilename(hint);
    if (filename == null) {
        // should not happen. It must be pre-rejected
        return new BluetoothOppReceiveFileInfo(BluetoothShare.STATUS_FILE_ERROR);
    }
    String extension = null;
    int dotIndex = filename.lastIndexOf(".");
    if (dotIndex < 0) {
        if (mimeType == null) {
            // should not happen. It must be pre-rejected
            return new BluetoothOppReceiveFileInfo(BluetoothShare.STATUS_FILE_ERROR);
        } else {
            extension = "";
        }
    } else {
        extension = filename.substring(dotIndex);
        filename = filename.substring(0, dotIndex);
    }
 
    if ((filename != null) && (filename.getBytes().length > OPP_LENGTH_OF_FILE_NAME)) {
      /* Including extn of the file, Linux supports 255 character as a maximum length of the
       * file name to be created. Hence, Instead of sending OBEX_HTTP_INTERNAL_ERROR,
       * as a response, truncate the length of the file name and save it. This check majorly
       * helps in the case of vcard, where Phone book app supports contact name to be saved
       * more than 255 characters, But the server rejects the card just because the length of
       * vcf file name received exceeds 255 Characters.
       */
      try {
          byte[] oldfilename = filename.getBytes("UTF-8");
          byte[] newfilename = new byte[OPP_LENGTH_OF_FILE_NAME];
          System.arraycopy(oldfilename, 0, newfilename, 0, OPP_LENGTH_OF_FILE_NAME);
          filename = new String(newfilename, "UTF-8");
      } catch (UnsupportedEncodingException e) {
          Log.e(Constants.TAG, "Exception: " + e);
      }
      if (D) Log.d(Constants.TAG, "File name is too long. Name is truncated as: " + filename);
    }
 
    filename = base.getPath() + File.separator + filename;
    // Generate a unique filename, create the file, return it.
    String fullfilename = chooseUniquefilename(filename, extension);
 
    if (!safeCanonicalPath(fullfilename)) {
        // If this second check fails, then we better reject the transfer
        return new BluetoothOppReceiveFileInfo(BluetoothShare.STATUS_FILE_ERROR);
    }
    if (V) Log.v(Constants.TAG, "Generated received filename " + fullfilename);
 
    if (fullfilename != null) {
        try {
            new FileOutputStream(fullfilename).close();
            int index = fullfilename.lastIndexOf('/') + 1;
            // update display name
            if (index > 0) {
                String displayName = fullfilename.substring(index);
                if (V) Log.v(Constants.TAG, "New display name " + displayName);
                ContentValues updateValues = new ContentValues();
                updateValues.put(BluetoothShare.FILENAME_HINT, displayName);
                context.getContentResolver().update(contentUri, updateValues, null, null);
 
            }
            return new BluetoothOppReceiveFileInfo(fullfilename, length, new FileOutputStream(
                    fullfilename), 0);
        } catch (IOException e) {
            if (D) Log.e(Constants.TAG, "Error when creating file " + fullfilename);
            return new BluetoothOppReceiveFileInfo(BluetoothShare.STATUS_FILE_ERROR);
        }
    } else {
        return new BluetoothOppReceiveFileInfo(BluetoothShare.STATUS_FILE_ERROR);
    }
 
}
 
private static boolean safeCanonicalPath(String uniqueFileName) {
    try {
        File receiveFile = new File(uniqueFileName);
        if (sDesiredStoragePath == null) {
            sDesiredStoragePath = Environment.getExternalStorageDirectory().getPath() +
                Constants.DEFAULT_STORE_SUBDIR;
        }
        String canonicalPath = receiveFile.getCanonicalPath();
 
        // Check if canonical path is complete - case sensitive-wise
        if (!canonicalPath.startsWith(sDesiredStoragePath)) {
            return false;
        }
 
        return true;
    } catch (IOException ioe) {
        // If an exception is thrown, there might be something wrong with the file.
        return false;
    }
}

修改方法:

root 就是存储的根目录。

如果需要将其修改之外部存储,修改此处的赋值即可。

如果需要修改子目录,修改base的拼接赋值即可。

此处修改需要注意,如果修改root或者base,则需要给sDesiredStoragePath重新赋值,使其一致,否则会导致safeCanonicalPath()判断会失败。
需要使完整的路径合法,否则无法接收文件。

结伴旅游,一个免费的交友网站:www.jieberu.com

推推族,免费得门票,游景区:www.tuituizu.com

Android Bluetooth 文件接收路径修改方法的更多相关文章

  1. Delphi获取文件名、不带扩展名文件名、文件所在路径、上级文件夹路径的方法

    1.获取不带扩展名的文件名方法,利用ChangeFileExt函数修改传入参数的扩展为空,并不会对文件本身产生变更. ChangeFileExt(ExtractFileName('D:\KK\Test ...

  2. asp.net 客户端上传文件全路径获取方法

    asp.net  获取客户端上传文件全路径方法: eg:F:\test\1.doc 基于浏览器安全问题,浏览器将屏蔽获取客户端文件全路径的方法,只能获取到文件的文件名,如果需要获取全路径则需要另想其他 ...

  3. Delphi XE的firemonkey获取当前文件所在路径的方法

    Delphi XE的firemonkey获取当前文件所在路径的方法 在之前,我们知道有三种方法: ExtractFilePath(ParamStr(0)) ExtractFilePath(Applic ...

  4. IOS获得各种文档文件夹路径的方法

    iphone沙箱模型的有四个目录,各自是什么,永久数据存储一般放在什么位置.得到模拟器的路径的简单方式是什么. documents,tmp.app,Library. (NSHomeDirectory( ...

  5. Xcode增加头文件搜索路径的方法

    Xcode增加头文件搜索路径的方法 以C++工程为例: 在Build Settings 页面中的Search Paths一节就是用来设置头文件路径. 相关的配置项用红框框起来了,共有三个配置项: He ...

  6. android获取各种系统路径的方法

    链接https://blog.csdn.net/qq_26296197/article/details/51909423 通过Environment获取的 Environment.getDataDir ...

  7. Oculus Store游戏下载默认路径修改方法

    最近在测试一款VR游戏,所以在硬件设备上选择了HTC Vive和Oculus两款眼镜.相对而言,HTC安装比较人性化:支持自定义安装路径,而且可在界面更改应用程序下载位置,如图所示: 这下替我节省了不 ...

  8. MAC在Finder栏显示所浏览文件夹路径的方法

    我们在使用MAC时,Finder栏默认只显示当前浏览的文件夹名称,而没有显示访问路径,这个问题该怎么解决呢? 操作步骤: 打开“终端”(应用程序->实用工具),输入以下两条命令: default ...

  9. MySQL参数文件及参数修改方法

    MySQL参数文件: MySQL数据库初始化参数由参数文件来设置,如果没有设置参数文件,mysql就按照系统中参数的默认值来启动. 在windows和linux上,参数文件可以被放在多个位置,数据库启 ...

随机推荐

  1. CNN(卷积神经网络)原理讲解及简单代码

    一.原理讲解 1. 卷积神经网络的应用 分类(分类预测) 检索(检索出该物体的类别) 检测(检测出图像中的物体,并标注) 分割(将图像分割出来) 人脸识别 图像生成(生成不同状态的图像) 自动驾驶 等 ...

  2. MAC_BOOKPRO苹果电脑系统常用快捷键大全

    Mac 键盘快捷键 我在品多多上拼的Mac终于到货了,安全下车,接下来要熟练使用了! 您可以按下某些组合键来实现通常需要鼠标.触控板或其他输入设备才能完成的操作.   要使用键盘快捷键,请按住一个或多 ...

  3. nginx 事件机制原理

    事件驱动模型是Nginx服务器保障完整功能和具有良好性能的重要机制之一. 事件驱动模型概述 实际上,事件驱动并不是计算机编程领域的专业词汇,它是一种比较古老的响应事件的模型,在计算机编程.公共关系.经 ...

  4. P1177快速排序

    这是一个快速排序的模板题.拿到题后便写了quicksort(确定一个基准数,利用两个哨兵,把大的放右边,小的放左边,再递归实现排序),但是竟然TLE了60pts(???),于是翻看dalao们的题解, ...

  5. APP登录时Token认证过程

    1.App登录Token登录机制: 一般第一次安装App后,会让你进行注册后登录,而只要登录成功后,以后的每次启动App都是登录状态, 不需要每次启动时再登录.但有些App你若长期没有启动,它会提示你 ...

  6. 什么是lambda函数?有什么好处?

    lambda 函数是一个可以接收任意多个参数(包括可选参数)并且返回单个表达式值的匿名函数 好处:1.lambda 函数比较轻便,即用即删除,很适合需要完成一项功能,但是此功能只在此一处使用,连名字都 ...

  7. java代码转化为jar包,再转化为.exe文件步骤

    下面是具体步骤: 一.先把自己的程序发布成jar文件 这是eclipse自带的功能,右键工程包-->Export 然后选择Java-->JAR file,next 选择输出路径,next ...

  8. CSUST 8.5 早训

    ## Problem A A - Meeting of Old Friends CodeForces - 714A 题意: 解题说明:此题其实是求两段区间的交集,注意要去除掉交集中的某个点. 题解: ...

  9. luogu P1232 [NOI2013]树的计数

    传送门 这题妙蛙 首先考虑构造出一个合法的树.先重新编号,把bfs序整成\(1,2,3...n\),然后bfs序就是按照从上到下从左往右的遍历顺序,所以可以考虑对bfs序分层,可以知道分层方式只会对应 ...

  10. Show Profile

    1.是什么:是mysql提供可以用来分析当前会话中语句执行的资源消耗情况.可以用于SQL的调优的测量 2.官网:http://dev.mysql.com/doc/refman/5.7/en/show- ...