专栏首页业余草如何在windows下和linux下获取文件(如exe文件)的详细信息和属性

如何在windows下和linux下获取文件(如exe文件)的详细信息和属性

程序员都很懒,你懂的!

最近在项目开发中,由cs开发的exe的程序,需要自动升级,该exe程序放在linux下,自动升级时检测不到该exe程序的版本号信息,但是我们客户端的exe程序需要获取服务器上新程序的版本号信息。最后由我用java实现linux上exe文件的版本号读取功能。下面是详细代码:

package com.herman.utils;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.RandomAccessFile;
/**
 * @see 获取文件信息的工具类
 * @author Herman.Xiong
 * @date 2014年5月12日 15:01:26
 * @version V1.0
 * @since tomcat 6.0 , jdk 1.6
 */
public class FileUtil {
	/**
	 * @see 获取版本信息
	 * @param filePath
	 * @return
	 */
	public static String getVersion(String filePath) {
		File file = new File(filePath);
		RandomAccessFile raf = null;
		byte[] buffer;
		String str;
		try {
			raf = new RandomAccessFile(file, "r");
			buffer = new byte[64];
			raf.read(buffer);
			str = "" + (char) buffer[0] + (char) buffer[1];
			if (!"MZ".equals(str)) {
				return null;
			}

			int peOffset = unpack(new byte[] { buffer[60], buffer[61],
					buffer[62], buffer[63] });
			if (peOffset < 64) {
				return null;
			}

			raf.seek(peOffset);
			buffer = new byte[24];
			raf.read(buffer);
			str = "" + (char) buffer[0] + (char) buffer[1];
			if (!"PE".equals(str)) {
				return null;
			}
			int machine = unpack(new byte[] { buffer[4], buffer[5] });
			if (machine != 332) {
				return null;
			}

			int noSections = unpack(new byte[] { buffer[6], buffer[7] });
			int optHdrSize = unpack(new byte[] { buffer[20], buffer[21] });
			raf.seek(raf.getFilePointer() + optHdrSize);
			boolean resFound = false;
			for (int i = 0; i < noSections; i++) {
				buffer = new byte[40];
				raf.read(buffer);
				str = "" + (char) buffer[0] + (char) buffer[1]
						+ (char) buffer[2] + (char) buffer[3]
						+ (char) buffer[4];
				if (".rsrc".equals(str)) {
					resFound = true;
					break;
				}
			}
			if (!resFound) {
				return null;
			}

			int infoVirt = unpack(new byte[] { buffer[12], buffer[13],
					buffer[14], buffer[15] });
			int infoSize = unpack(new byte[] { buffer[16], buffer[17],
					buffer[18], buffer[19] });
			int infoOff = unpack(new byte[] { buffer[20], buffer[21],
					buffer[22], buffer[23] });
			raf.seek(infoOff);
			buffer = new byte[infoSize];
			raf.read(buffer);
			int numDirs = unpack(new byte[] { buffer[14], buffer[15] });
			boolean infoFound = false;
			int subOff = 0;
			for (int i = 0; i < numDirs; i++) {
				int type = unpack(new byte[] { buffer[i * 8 + 16],
						buffer[i * 8 + 17], buffer[i * 8 + 18],
						buffer[i * 8 + 19] });
				if (type == 16) { // FILEINFO resource
					infoFound = true;
					subOff = unpack(new byte[] { buffer[i * 8 + 20],
							buffer[i * 8 + 21], buffer[i * 8 + 22],
							buffer[i * 8 + 23] });
					break;
				}
			}
			if (!infoFound) {
				return null;
			}

			subOff = subOff & 0x7fffffff;
			infoOff = unpack(new byte[] { buffer[subOff + 20],
					buffer[subOff + 21], buffer[subOff + 22],
					buffer[subOff + 23] }); // offset of first FILEINFO
			infoOff = infoOff & 0x7fffffff;
			infoOff = unpack(new byte[] { buffer[infoOff + 20],
					buffer[infoOff + 21], buffer[infoOff + 22],
					buffer[infoOff + 23] }); // offset to data
			int dataOff = unpack(new byte[] { buffer[infoOff],
					buffer[infoOff + 1], buffer[infoOff + 2],
					buffer[infoOff + 3] });
			dataOff = dataOff - infoVirt;

			int version1 = unpack(new byte[] { buffer[dataOff + 48],
					buffer[dataOff + 48 + 1] });
			int version2 = unpack(new byte[] { buffer[dataOff + 48 + 2],
					buffer[dataOff + 48 + 3] });
			int version3 = unpack(new byte[] { buffer[dataOff + 48 + 4],
					buffer[dataOff + 48 + 5] });
			int version4 = unpack(new byte[] { buffer[dataOff + 48 + 6],
					buffer[dataOff + 48 + 7] });
			System.out.println(version2 + "." + version1 + "." + version4 + "."
					+ version3);
			return version2 + "." + version1 + "." + version4 + "." + version3;
		} catch (FileNotFoundException e) {
			return null;
		} catch (IOException e) {
			return null;
		} finally {
			if (raf != null) {
				try {
					raf.close();
				} catch (IOException e) {
				}
			}
		}
	}

	public static int unpack(byte[] b) {
		int num = 0;
		for (int i = 0; i < b.length; i++) {
			num = 256 * num + (b[b.length - 1 - i] & 0xff);
		}
		return num;
	}
}

运行效果图(window上和linux的filePath自己改正正确即可):

点击下载详细的演示项目http://download.csdn.net/detail/xmt1139057136/7335155

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • 防治运营商HTTP劫持的终极技术手段

    运营商HTTP劫持(非DNS劫持)推送广告的情况相信大家并不陌生,解决的方法大多也是投诉增值业务部门进而投诉工信部。但这种方法...

    业余草
  • Cache 和 Buffer 都是缓存,主要区别是什么?

    原文链接:https://www.zhihu.com/question/26190832/answer/8306151...

    业余草
  • ant的高级使用,ant命令详解,ant打包,ant编译后打包去掉jar文件

    在日常的项目开发中,我们可以经常性的需要打包测试,尤其是开发环境是windows,而实际环境则是linux。 这样的话,很...

    业余草
  • GNU emacs Lisp小结3

    chapter4 与缓冲区有关的函数 4.1 查找更多的信息 C-h f 函数名   ;查询函数 C-h v 变量名   ;查询变量 find-tags 函数 ...

    py3study
  • 2.4 图形硬件

    这一节中主要阐述图形硬件的相关知识,主要包括 GPU 中数据的存放硬件, 以及各类缓冲区的具体含义和用途,如:z buffer(深度缓冲区)、stencil b...

    代码咖啡
  • C语言实现数组的循环左移,右移,翻转

    morixinguan
  • Netty 异步的、事件驱动的网络应用程序框架和工具

    Netty是由JBOSS提供的一个Java开源框架。Netty提供异步的、事件驱动的网络应用程序框架和工具,用以快速开发高性能、高可靠性的网络服务器和客户端程序...

    WindWant
  • 第四节 netty前传-NIO中缓冲buffer-02

    equals仅比较缓冲区的一部分,而不是它内部的每个元素。 实际上,它只是比较缓冲区中的其余元素。compareTo()方法比较两个缓冲区的剩余元素(字节,字符...

    用户1418372
  • mysql join和sort的buffer

    参数查看命令 SELECT @@join_buffer_size; SELECT @@sort_buffer_size; join_buffer_size 当...

    dys
  • EMLOG无插件实现网站源码压缩

    在以往的Emlog优化教程中,相信都是使用的代码压缩插件,今天主要是分享插件的代码版本,也就是不使用插件,直接将代码丢在module.php中就可以,好吧,又消...

    似水的流年

扫码关注云+社区

领取腾讯云代金券