利用SVN实现自动修订版本号生成


自:http://hi.baidu.com/comeon010/blog/item/67c5669bfa759eb8c8eaf42a.html

SVN是当前比较流行的版本控制软件,下面主要介绍通过SVN在程序编译时自动生成版本号。

基本思想:利用SubWCRev.exe获取版本信息,读入屏幕流,生成包括版本号信息的“.H文件”,并修改“.rc资源文件”中的版本信息,“.H文件”主要用于关于框中的版本显示,简单格式如下:

#ifndef __SVN_VERSION_MAX
#define __SVN_VERSION_MAX XXX
#endif

用下面附录的源码编译SVNVersionGen.exe

使用说明:

建立一个批处理文件

setlocal

设置TortoiseSVN安装目录
set SVN_PATH=D:\Program Files\TortoiseSVN\bin  
设置解决方案目录
set WORK_DIR=e:\My Documents\Visual Studio Projects\XXX
设置版本号,前三位
set VERSION_M="1,X,X"
set VERSION_S="1, X, X"

SVNVersionGen -HEADER "%SVN_PATH%" "%WORK_DIR%" "SVNVersion.h"

设置子项目名称
set PRO1_NAME=PROJECT1
SVNVersionGen -RESVERSION "%SVN_PATH%" "%WORK_DIR%\%PRO1_NAME%" "%WORK_DIR%\%PRO1_NAME%\%PRO1_NAME%.rc" %VERSION_M% %VERSION_S%

设置子项目2名称
set PRO1_NAME=PROJECT2
SVNVersionGen -RESVERSION "%SVN_PATH%" "%WORK_DIR%\%PRO1_NAME%" "%WORK_DIR%\%PRO1_NAME%\%PRO1_NAME%.rc" %VERSION_M% %VERSION_S%
endlocal


源码:

// SVNVersionGen.cpp

#include "stdafx.h"
#include<string>
#include<windows.h>
#include<iostream>
using namespace std;

int GetSVNVersion( const char* pProPath,const char* pWorkDir,int& nVer,string& strOut )
{
nVer = 0;
string strInfo;
SECURITY_ATTRIBUTES sa;
HANDLE hRead,hWrite;

 sa.nLength = sizeof(SECURITY_ATTRIBUTES);
sa.lpSecurityDescriptor = NULL;
sa.bInheritHandle = TRUE;
if (!CreatePipe(&hRead,&hWrite,&sa,0)) 
{
return -1;

STARTUPINFO si;
PROCESS_INFORMATION pi; 
si.cb = sizeof(STARTUPINFO);
GetStartupInfo(&si); 
si.hStdError = hWrite;
si.hStdOutput = hWrite;
si.wShowWindow = SW_HIDE;
si.dwFlags = STARTF_USESHOWWINDOW | STARTF_USESTDHANDLES;

 char strPro[MAX_PATH];
sprintf( strPro,"%s\\SubWCRev.exe \"%s\"",pProPath,pWorkDir );
if (!CreateProcess(NULL,strPro,NULL,NULL,TRUE,NULL,NULL,NULL,&si,&pi)) 
{
return -1;
}
CloseHandle(hWrite);

 char buffer[4096] = {0};
DWORD bytesRead; 
while(true) 
{
if(ReadFile(hRead,buffer,4095,&bytesRead,NULL) == NULL)
break;
strInfo += buffer;
Sleep(200); 
}

 char strCon[4096];
strcpy( strCon,"SubWCRev: '" );
strcat( strCon,pWorkDir );
strcat( strCon,"'\nLast committed at revision %d\n" );
sscanf( strInfo.c_str(),strCon,&nVer);

 int nn = 0;
for( int i =0;i<strInfo.length();i++ )
{
if( strInfo[i] == '\n' )
{
nn++;
continue;
}
if( nn >= 3 )
{
break;
}
if( nn >= 2 )
{
if( strInfo[i] != '\r' )
strOut.push_back(strInfo[i]);
}
}

 return 0;
}

int main(int argc, char* argv[])
{
if( argc < 2 )
{
return 0;
}
if( strcmp(argv[1],"-HEADER")==0 )
{
if( argc <= 4 )
{
return 0;
}
int nVer = 0;
string strOut;
GetSVNVersion( argv[2],argv[3],nVer,strOut );
cout<<nVer<<endl;
if( nVer > 0 )
{
FILE* f = fopen( argv[4],"w" );
if( f )
{
fprintf( f,"#ifndef __SVN_VERSION_MAX\n" );
fprintf( f,"#define __SVN_VERSION_MAX %d\n",nVer+1 );
fprintf( f,"static const int __SVN_VERSION = %d;\n",nVer+1 );
fprintf( f,"#endif\n" );
fclose(f);
MessageBox(0,"成功生成版本头文件","",0);
}
}
else
{
MessageBox(0,"生成版本头文件失败","",0);
}
return 0;
}
if( strcmp(argv[1],"-RESVERSION")==0 )
{
if( argc <= 6 )
{
MessageBox(0,"更新资源文件版本号失败","",0);
return 0;
}
int nVer = 0;
string strOut;
GetSVNVersion( argv[2],argv[3],nVer,strOut );
//MessageBox(0,strOut.c_str(),"",0);
if( nVer <= 0 )
{
MessageBox(0,argv[4],"更新资源文件版本号失败",0);
return 0;
}
nVer ++;

char buf[4096];
char fileo[MAX_PATH];
strcpy( fileo,argv[4] );
strcat( fileo,".o");
FILE* fw = fopen( fileo,"w" );
FILE* f = fopen( argv[4],"r" );
while( fgets(buf,sizeof(buf),f) > 0 )
{
char* p = NULL;
if( (p=strstr(buf, "            VALUE \"Comments\"")) != NULL )
{
fprintf( fw,"            VALUE \"Comments\", \"%s\"\n",strOut.c_str());
printf("%s",p);
continue;
}
else if( (p=strstr(buf, " FILEVERSION ")) != NULL )
{
fprintf( fw," FILEVERSION %s,%d\n",argv[5],nVer);
printf("%s",p);
continue;
}
else if( (p=strstr(buf, " PRODUCTVERSION ")) != NULL )
{
fprintf( fw," PRODUCTVERSION %s,%d\n",argv[5],nVer);
printf("%s",p);
continue;
}
else if( (p=strstr(buf, "            VALUE \"FileVersion\", ")) != NULL )
{
fprintf( fw,"            VALUE \"FileVersion\", \"%s, %d\"\n",argv[6],nVer);
printf("%s",p);
continue;
}
else if( (p=strstr(buf, "            VALUE \"ProductVersion\"")) != NULL )
{
fprintf( fw,"            VALUE \"ProductVersion\", \"%s ,%d\"\n",argv[6],nVer);
printf("%s",p);
continue;
}
fprintf( fw,"%s",buf );
}
fclose( f );
fclose( fw );
char filebak[MAX_PATH];
strcpy( filebak,argv[4] );
strcat( filebak,".bak");
::DeleteFile( filebak );
rename( argv[4],filebak );
::DeleteFile( argv[4] );
rename( fileo,argv[4] );
MessageBox(0,argv[4],"成功更新版本号",0);
}
}

你可能感兴趣的:(利用SVN实现自动修订版本号生成)