• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>

            戰(zhàn)魂小筑

            討論群:309800774 知乎關(guān)注:http://zhihu.com/people/sunicdavy 開源項(xiàng)目:https://github.com/davyxu

               :: 首頁 :: 新隨筆 :: 聯(lián)系 :: 聚合  :: 管理 ::
              257 隨筆 :: 0 文章 :: 506 評(píng)論 :: 0 Trackbacks

            #

            先說下我的工程目錄

            ProjectName\

            src\

              core\

              share\

              proj.android\

                jni\

                …

            sdk\

              protobuf-2.4.1\

                src\

                …

            從Google code下載protobuf-2.4.1源碼包, 解壓, 在protobuf-2.4.1目錄下添加Android.mk, 內(nèi)容如下

            LOCAL_PATH := $(call my-dir)
             
            include $(CLEAR_VARS)
             
            LOCAL_MODULE := protobuf-2.4.1
             
            LOCAL_SRC_FILES := \
            src/google/protobuf/io/coded_stream.cc                \
            src/google/protobuf/io/printer.cc                     \
            src/google/protobuf/io/gzip_stream.cc                 \
            src/google/protobuf/io/tokenizer.cc                   \
            src/google/protobuf/io/zero_copy_stream.cc            \
            src/google/protobuf/io/zero_copy_stream_impl.cc       \
            src/google/protobuf/io/zero_copy_stream_impl_lite.cc  \
            src/google/protobuf/stubs/common.cc                   \
            src/google/protobuf/stubs/once.cc                     \
            src/google/protobuf/stubs/structurally_valid.cc       \
            src/google/protobuf/stubs/strutil.cc                  \
            src/google/protobuf/stubs/substitute.cc               \
            src/google/protobuf/compiler/importer.cc              \
            src/google/protobuf/compiler/parser.cc                \
            src/google/protobuf/descriptor.cc                     \
            src/google/protobuf/descriptor.pb.cc                  \
            src/google/protobuf/descriptor_database.cc            \
            src/google/protobuf/dynamic_message.cc                \
            src/google/protobuf/extension_set.cc                  \
            src/google/protobuf/extension_set_heavy.cc            \
            src/google/protobuf/generated_message_reflection.cc   \
            src/google/protobuf/generated_message_util.cc         \
            src/google/protobuf/message.cc                        \
            src/google/protobuf/message_lite.cc                   \
            src/google/protobuf/reflection_ops.cc                 \
            src/google/protobuf/repeated_field.cc                 \
            src/google/protobuf/service.cc                        \
            src/google/protobuf/text_format.cc                    \
            src/google/protobuf/unknown_field_set.cc              \
            src/google/protobuf/wire_format.cc                    \
            src/google/protobuf/wire_format_lite.cc               \
             
             
            LOCAL_C_INCLUDES := $(LOCAL_PATH) \
                                $(LOCAL_PATH)/src
                               
             
            include $(BUILD_STATIC_LIBRARY)

            此時(shí)編譯會(huì)報(bào)config.h找不到的錯(cuò)誤, 這個(gè)文件在vsproject目錄有, 但只是VC編譯使用,  這篇文章說需要手動(dòng)創(chuàng)建, 但實(shí)際上, Linux下可以通過config系統(tǒng)自動(dòng)生成的, 但是Android平臺(tái)下,不使用cygwin時(shí), 就需要自己手動(dòng)創(chuàng)建config.h, 內(nèi)容如下

            /*
                This make file is only for android ONLY, modified by Davy Xu June 17, 2013
                Cause android platform can't use linux config system when cygwin envirement is not available
            */
             
            /* the location of <hash_set> */
            #define HASH_SET_H <ext/hash_set>
            #define HASH_MAP_H <ext/hash_map>
            #define HASH_NAMESPACE __gnu_cxx
             
            /* define if the compiler has hash_map */
            //#define HAVE_HASH_MAP 1
             
            /* define if the compiler has hash_set */
            //#define HAVE_HASH_SET 1
             
            #define HAVE_PTHREAD

            剩下的事情就簡(jiǎn)單了, 在你的工程Android.mk里添加protobuf的引用

            例如:

            LOCAL_WHOLE_STATIC_LIBRARIES += protobuf-2.4.1

            $(call import-module,protobuf-2.4.1)

            還要在NDK_MODULE_PATH中增加搜索路徑D:\Develop\ProjectName\sdk\

            注意, 這里protobuf-2.4.1名稱必須與sdk下的文件夾名, LOCAL_MODULE中的名稱保持一致, 否則搜索不到

            posted @ 2013-06-17 11:40 戰(zhàn)魂小筑 閱讀(5452) | 評(píng)論 (0)編輯 收藏

            最近將cocos2dx的程序移植到Android上, 某階段突然發(fā)現(xiàn)開始閃退. 日志方式跟了很久, 發(fā)現(xiàn)有內(nèi)存被修改. 因?yàn)椴荒芟馰C那樣有內(nèi)存斷點(diǎn), 只有靠日志繼續(xù)跟蹤, 繞了很久, 終于發(fā)現(xiàn)一個(gè)問題

            CCApplication::sharedApplication()->run(); 在Windows下除了初始化回調(diào)外, 還有Windows平臺(tái)特殊的消息循環(huán). 既然是循環(huán), 這個(gè)run函數(shù)會(huì)一直阻塞到程序退出, 因此我自然的在run后添加自己的資源卸載

            換到Android上呢CCApplication::sharedApplication()->run();的實(shí)現(xiàn)變了. 由于Android上沒有Windows的消息循環(huán), 所有事件都是通過java方式的事件通知. 因此CCApplication::sharedApplication()->run();變成了非阻塞, 可是我在run后添加了資源卸載. 結(jié)果導(dǎo)致系統(tǒng)剛初始化就卸載了資源, 內(nèi)存直接不可用, 導(dǎo)致后面cocos2dx的API部分使用無問題, 而自己引擎的API調(diào)用閃退.

            cocos2dx的這個(gè)run函數(shù)命名有嚴(yán)重問題.. 被坑了好久, 還一直懷疑NDK內(nèi)存管理是否有特殊之處, 殊不知..

            posted @ 2013-06-14 17:15 戰(zhàn)魂小筑 閱讀(9822) | 評(píng)論 (5)編輯 收藏

            本文整個(gè)部署過程無需下載及安裝使用Cygwin環(huán)境, 以下部署過程需要用到的程序及版本

            請(qǐng)注意下載對(duì)應(yīng)你系統(tǒng)的版本, 64位系統(tǒng)請(qǐng)保證后文全系使用64位程序, 以免遇到不必要的麻煩

            1.JDK&JRE       JAVA運(yùn)行時(shí)及開發(fā)包

            2.ADT               是Eclipse的一個(gè)插件,這一步是為了管理安卓開發(fā)庫(kù)

            http://developer.android.com/sdk/index.html

            作為新手, 請(qǐng)下載ADT Bundle For Windows, 這個(gè)版本已經(jīng)包含

            ADK(安卓開發(fā)包), CDT(Eclipse的C/C++開發(fā)插件)及對(duì)應(yīng)的Eclipse, 可以避免第一次部署出現(xiàn)的各種煩心!

            3.NDK              只有ADT已經(jīng)可以運(yùn)行普通的Andriod程序,但是如果需要編譯C/C++程序, 還需要NDK

            http://developer.android.com/tools/sdk/ndk/index.html

            4. cocos2dx 2.0.4版本

             

            準(zhǔn)備SDK API

            下載好ADT后解壓, 有如下目錄

            eclipse\      <- 開發(fā)環(huán)境

            sdk\           <- Andriod SDK

            SDK Manager.exe     <-- Android開發(fā)包管理器, 由于Andriod版本較多, 所以此管理器可以方便開發(fā)者選擇部署目標(biāo)機(jī)器

            打開SDK Manager在Android 2.2(API 8)里的 SDK Platform, Google APIs前打勾, 點(diǎn)擊右下角的Instal packages

            如果感覺下載速度慢, 可以移步這里http://my.oschina.net/heguangdong/blog/17443, 選擇Andriod離線下載

            這里是下載鏈接

            http://dl-ssl.google.com/android/repository/google_apis-8_r02.zip

            http://dl-ssl.google.com/android/repository/android-2.2_r02-windows.zip

            https://dl-ssl.google.com/android/repository/usb_driver_r04-windows.zip

            把a(bǔ)ndroid開頭的文件解壓到platforms目錄下

            把goole_apis開頭的文件解壓到add-ons目錄下

            把usb_driver_r03-windows.zip解壓到usb_driver目錄下。

            Eclipse導(dǎo)入工程

            打開Eclipse

            導(dǎo)入Cocos2dx例子工程:

            Eclipse中File->New->Other...選擇Andriod Project from Existing Code

            在Import Projects的Root Directory中導(dǎo)入D:\Develop\RevWar\sdk\cocos2d-2.0-x-2.0.4\samples\HelloCpp\proj.android\

            注意, 不要選中 Copy project into workspace, 否則路徑編亂很難編譯成功

             

            導(dǎo)入cocos2dx的java框架

            在src目錄中new package, 輸入org.cocos2dx.lib, 在org.cocos2dx.lib的package中點(diǎn)Import-> FileSystem

            選中目錄D:\Develop\RevWar\sdk\cocos2d-2.0-x-2.0.4\cocos2dx\platform\android\java\src\org\cocos2dx\lib\, 點(diǎn)選所有java文件

            工程Properties->Builder->New->Program

            在Main標(biāo)簽中填寫

            填寫NDK編譯命令行 D:\Develop\android-ndk-r8e\ndk-build.cmd

            點(diǎn)擊Browser Workspace選中當(dāng)前工程,出現(xiàn)${workspace_loc:/HelloCpp}

            切換到Environment標(biāo)簽中填寫

            新建NDK_MODULE_PATH 填寫D:\Develop\RevWar\sdk\cocos2d-2.0-x-2.0.4\;D:\Develop\RevWar\sdk\cocos2d-2.0-x-2.0.4\cocos2dx\platform\third_party\android\prebuilt\

            修改cocos2dx的Android.mk, diff如下

            @@ -153,6 +153,7 @@

            LOCAL_WHOLE_STATIC_LIBRARIES += cocos_jpeg_static

            LOCAL_WHOLE_STATIC_LIBRARIES += cocos_libxml2_static

            LOCAL_WHOLE_STATIC_LIBRARIES += cocos_libtiff_static

            +LOCAL_WHOLE_STATIC_LIBRARIES += cocosdenshion_static

            # define the macro to compile through support/zip_support/ioapi.c              

            LOCAL_CFLAGS := -DUSE_FILE32API

            @@ -164,3 +165,4 @@

            $(call import-module,libpng)

            $(call import-module,libxml2)

            $(call import-module,libtiff)

            +$(call import-module,CocosDenshion/android)

            F&Q

            andriod-8問題

            修改D:\Develop\RevWar\sdk\cocos2d-2.0-x-2.0.4cocos2dx\platform\android\java\project.properties中的target=android-8改成你需要的版本

            resources.ap_ does not exist

            assert目錄中有資源出問題, 排查即可

            例如: cocos2d-2.0-x-2.0.4\samples\TestCpp\proj.android\assets\Images\*.pvr.gz

            啟動(dòng)Android模擬器時(shí)的Failed to allocate memory: 8問題

            調(diào)整內(nèi)存值,請(qǐng)求內(nèi)存太大導(dǎo)致

            api版本過低導(dǎo)致JAVA Symbol未定義問題

            setEGLContextClientVersion undefined

            api8(andriod 2.2)后的版本, 才支持openGL es 2.0

            自己做工程遇到的問題D:\Develop\RevWar\sdk\cocos2d-2.0-x-2.0.4\/cocos2dx/platform/android/jni/JniHelper.h:28:18: fatal error: string: No such file or directory

            將cocos2dx例子中的Application.mk拷過來, 修改下內(nèi)部名稱即可

            調(diào)試請(qǐng)盡量使用真機(jī), 模擬器速度很慢

            小米2默認(rèn)只能管理文件, 無法用adb 連接, 因此需要安裝驅(qū)動(dòng), USB驅(qū)動(dòng)直接在插入電腦后的虛擬盤里找.. 這個(gè)太坑了..

            保證每次都能部署最新的程序

            請(qǐng)執(zhí)行每次Clean, Build project, Debug.  真機(jī)上在需要時(shí), 會(huì)彈出安裝...

            Android啟動(dòng)日志

            帶有ADT的Eclipse中有一個(gè)logcat窗口, 里面有系統(tǒng)及程序本身的日志, 可以做過濾,方便檢查問題. 如需自己打日志, 可以使用cocos2dx中的LOGD宏來做, 原型是__android_log_print(ANDROID_LOG_DEBUG,LOG_TAG,__VA_ARGS__)

             

            Remark

            添加assert后, F5刷新后再編譯
            NDK build時(shí),默認(rèn)從工程的jni目錄開始

            Andriod.mk的import 原則$(call import-module,模塊名) 這里的模塊名必須與目錄名, 模塊make file中的名稱報(bào)紙一致

            參考文章

            http://www.cnblogs.com/ybgame/archive/2012/06/07/2540693.html

            發(fā)文時(shí), Andriod Studio已經(jīng)發(fā)布了一段時(shí)間, 雖然是測(cè)試版, 但將代表未來更方便的Andriod發(fā)布工具

            posted @ 2013-06-09 17:55 戰(zhàn)魂小筑 閱讀(19070) | 評(píng)論 (0)編輯 收藏

               最近開始弄cocos2dx, 圖片需要整合成POT的優(yōu)化紋理, 使用texturePacker來做
            下載http://www.codeandweb.com/texturepacker/download
            工具本身不是免費(fèi)的, 但是可以通過申請(qǐng)獲得免費(fèi)的Licence, 點(diǎn)這里
            條件是有一個(gè)自己的博客, 并且從事游戲/軟件/網(wǎng)頁方面的開發(fā), 且近期有5篇文章發(fā)表
            作者特別強(qiáng)調(diào),微博不等于博客

            填寫好郵箱地址,要不了幾個(gè)小時(shí)就可以獲取到序列號(hào)
            posted @ 2013-06-05 15:44 戰(zhàn)魂小筑 閱讀(2538) | 評(píng)論 (1)編輯 收藏

            https://code.google.com/p/protoc-gen-lua/ 下載網(wǎng)易兄弟寫的lua的protobuf插件(網(wǎng)易都把pb給弄完了,as3的也是他們寫的..)

             

            編譯python版的protobuf模塊

            https://code.google.com/p/protobuf/downloads/list 下載官方的原生版本protobuf, 這里發(fā)文時(shí)使用的是2.4.1版本

            編譯出protoc執(zhí)行文件, 放一份在protobuf-2.4.1\src\下

            下載python2.7版本, 在protobuf-2.4.1\python下運(yùn)行python setup.py install(如果找不到python請(qǐng)給python絕對(duì)路徑)

            這一步, python會(huì)下一個(gè)蛋( 真的是一個(gè)python的egg文件 ), 然后編譯出python版本的protobuf模塊放置在python下

             

            制作protoc-gen-lua的批處理

            放一份protoc在protoc-gen-lua的plugin目錄

            編寫批處理:protoc-gen-lua.bat

            @python "%~dp0protoc-gen-lua"

             

            協(xié)議目錄生成腳本

            在你需要放置協(xié)議的目錄編寫如下批處理

            buildproto.bat

            rd /S /Q .\%1%
            "..\..\src\protoc-gen-lua\plugin\protoc.exe" --plugin=protoc-gen-lua="..\..\src\protoc-gen-lua\plugin\protoc-gen-lua.bat" --lua_out=. %1%.proto

            注意protoc.exe及protoc-gen-lua.bat的路徑符合你的路徑

            再編寫要編譯的proto協(xié)議的批處理generate.bat

            call buildproto.bat loginsvc

            執(zhí)行g(shù)enerate.bat后, 將會(huì)編譯同目錄下的loginsvc.proto,輸出loginsvc_pb.lua

             

            編譯鏈接lua的pb庫(kù)

            將protoc-gen-lua\protobuf\目錄拷貝到之前的協(xié)議目錄

            將其下的pb.c鏈入你的工程, 注意VS2010的VC下需要修改源碼

            1.將 #include <endian.h>修改為

            #ifndef _WIN32
                 #include <endian.h>
                 #endif

            避免在windows下缺失文件報(bào)錯(cuò).

            2. 調(diào)整struct_unpack函數(shù)前幾行為

            static int struct_unpack(lua_State *L)
            {
                uint8_t format = luaL_checkinteger(L, 1);
                size_t len;
                const uint8_t* buffer = (uint8_t*)luaL_checklstring(L, 2, &len);
                size_t pos = luaL_checkinteger(L, 3);
                uint8_t out[8];   

                buffer += pos;

            避免VS2010的VC編譯器過于標(biāo)準(zhǔn), 嚴(yán)格要求C風(fēng)格函數(shù)變量前置聲明

            在lua_State聲明后添加如下代碼

            extern "C" { int luaopen_pb (lua_State *L);}   // 注意防在命名空間外的全局聲明

                luaopen_pb( L );   // 直接注入全局pb, 避免動(dòng)態(tài)加載pb.dll造成的一系列跨平臺(tái)問題

             

            lua中使用pb

            local loginsvc_pb = require “loginsvc_pb”
             
            local REQ = loginsvc_pb.CheckVersionREQ()
            local Data = REQ:SerializeToString( )
             
            local ACK = loginsvc_pb.CheckVersionACK()
            ACK:ParseFromString( Data )

             

            .csharpcode, .csharpcode pre { font-size: small; color: black; font-family: consolas, "Courier New", courier, monospace; background-color: #ffffff; /*white-space: pre;*/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt { background-color: #f4f4f4; width: 100%; margin: 0em; } .csharpcode .lnum { color: #606060; }

            我的工程目錄

            script\
                    protobuf\
                        buildproto.bat
                        generate.bat
                        loginsvc_pb.lua
                        loginsvc.proto
                    Main.lua
                src\
                    protoc-gen-lua\
                        example\
                        plugin\
                        protobuf\

            posted @ 2013-04-24 15:44 戰(zhàn)魂小筑 閱讀(13500) | 評(píng)論 (4)編輯 收藏

            為了降低模塊間的耦合, 很多系統(tǒng)使用事件派發(fā)機(jī)制, 接收方無需知道派發(fā)者是誰.在Qt中,這個(gè)系統(tǒng)被稱作Slot&Signal, 需要配合moc代碼生成機(jī)制, 但是系統(tǒng)本身是線程安全的.

            這里我們討論的是lua的事件派發(fā)機(jī)制, 我將此寫成lua模塊, 方便配合cocos2dx進(jìn)行邏輯處理

             

            local Global = _G
            local package = _G.package
            local setmetatable = _G.setmetatable
            local assert = _G.assert
            local table = _G.table
            local pairs = _G.pairs
            local ipairs = _G.ipairs
             
             
            module "Core.EventDispatcher"
             
            --[[
            數(shù)據(jù)層次
             
            ["EventName1"] =
            {
                ["_StaticFunc"] = { Func1, Func2 },
                
                [Object1] = { Func1, Func2 },
                [Object2] = { Func1, Func2 },
            },
             
            ["EventName2"] =
            {
                ...
            }
             
            ]]
             
            -- 默認(rèn)調(diào)用函數(shù)
            local function PreInvoke( EventName, Func, Object, UserData, ... )
                
                if Object then
                    Func( Object, EventName, ... )
                else
                    Func( EventName, ... )
                end
             
            end
             
            function New( )    
                
                local NewObj = setmetatable( {}, { __index = package.loaded["Core.EventDispatcher"] } )
                
                -- 對(duì)象成員初始化
                NewObj.mPreInvokeFunc = PreInvoke
                NewObj.mEventTable = {}
                
                return NewObj
            end
             
            -- 添加
            function Add( Self, EventName, Func, Object, UserData )
             
                assert( Func )
             
                Self.mEventTable[ EventName ] = Self.mEventTable[ EventName ] or {}
                
                local Event = Self.mEventTable[ EventName ]
                
                if not Object then
                    Object = "_StaticFunc"
                end
                
                Event[Object] = Event[Object] or {}
                local ObjectEvent = Event[Object]
             
                ObjectEvent[Func] = UserData or true
                
            end
             
            -- 設(shè)置調(diào)用前回調(diào)
            function SetDispatchHook( Self, HookFunc )
                
                Self.mPreInvokeFunc = HookFunc
            end
             
             
            -- 派發(fā)
            function Dispatch( Self, EventName, ... )
             
                assert( EventName )
                
                local Event = Self.mEventTable[ EventName ]
                
                for Object,ObjectFunc in pairs( Event ) do
                    
                    if Object == "_StaticFunc" then
                            
                        for Func, UserData in pairs( ObjectFunc ) do
                            Self.mPreInvokeFunc( EventName, Func, nil, UserData, ... )    
                        end
                        
                    else
                    
                        for Func, UserData in pairs( ObjectFunc ) do
                            Self.mPreInvokeFunc( EventName, Func, Object, UserData, ... )
                        end
                    
                    end
             
                end
             
            end
             
            -- 回調(diào)是否存在
            function Exist( Self, EventName )
             
                assert( EventName )
                
                local Event = Self.mEventTable[ EventName ]
                
                if not Event then
                    return false
                end
                
                -- 需要遍歷下map, 可能有事件名存在, 但是沒有任何回調(diào)的
                for Object,ObjectFunc in pairs( Event ) do
                
                    for Func, _ in pairs( ObjectFunc ) do
                        -- 居然有一個(gè)
                        return true
                    end
                
                end
                
                
                return false
                
            end
             
            -- 清除
            function Remove( Self, EventName, Func, Object )
                
                assert( Func )
                
                local Event = Self.mEventTable[ EventName ]
                
                if not Event then
                    return
                end
                
                if not Object then
                    Object = "_StaticFunc"
                end
                
                
                local ObjectEvent = Event[Object]
                
                if not ObjectEvent then
                    return
                end
                
                ObjectEvent[Func] = nil
             
                    
            end
             
            -- 清除對(duì)象的所有回調(diào)
            function RemoveObjectAllFunc( Self, EventName, Object )
             
                assert( Object )
                
                local Event = Self.mEventTable[ EventName ]
                
                if not Event then
                    return
                end
                
                Event[Object] = nil
             
            end
             

            這里注意下, 我是將EventDispatcher.lua放置在Core目錄下, 因此需要使用require “Core.EventDispatcher”進(jìn)行調(diào)用

            使用用例

             

                local EventDispatcher = require 'Core.EventDispatcher'
             
                local E = EventDispatcher.New()
             
             
                E:Add( "a", function( a, b )   print( a, b ) end )
             
                local Func = function( a )   print( a ) end 
                E:Add( "a", Func )
             
             
                E:Dispatch("a", 1, 2 )
                print( E:Exist("a"), E:Exist("b"))
             
                E:Remove("a", Func )
             
                E:Dispatch("a", 1, 2 )
                print( E:Exist("a"), E:Exist("b"))
            posted @ 2013-04-24 15:19 戰(zhàn)魂小筑 閱讀(7064) | 評(píng)論 (0)編輯 收藏

            Linux上跑服務(wù)器如果遇到程序崩潰是一件很苦惱的事情, 再碰到重現(xiàn)很難的BUG, 估計(jì)只能通過傳統(tǒng)的排查方法進(jìn)行.

            在編寫本文前, 筆者使用過諸如libunwind等庫(kù)進(jìn)行錯(cuò)誤時(shí)堆棧打印, 但是其本身由于需要引用第三方庫(kù), 使用還是稍微麻煩.

            經(jīng)過Google后, 居然找到一篇好文, 其通過捕獲SIGSEGV信號(hào), 并迫使程序進(jìn)入gdb調(diào)試階段, 利用gdb強(qiáng)大的調(diào)試功能可以進(jìn)行各種錯(cuò)誤跟蹤, 此法已與Windows下程序崩潰后彈出VC調(diào)試幾乎接近.

            我在此文基礎(chǔ)上, 擴(kuò)展了其通用性及便利性

            1. 使用gdb的 -ex參數(shù), 在掛接程序后, 執(zhí)行bt指令打出程序堆棧

            2. 將信息重定向到自定義的文件,在多進(jìn)程都需要進(jìn)行后臺(tái)輸出時(shí)帶來更大的靈活性, 同時(shí)也解決了gdb只能在前臺(tái)調(diào)試的問題

            代碼如下

            #include <stdio.h>
            #include <stdlib.h>
            #include <signal.h>
            #include <string.h>
            
            void dump(int signo)
            {
                    char buf[1024];
                    char cmd[1024];
                    FILE *fh;
            
                    snprintf(buf, sizeof(buf), "/proc/%d/cmdline", getpid());
                    if(!(fh = fopen(buf, "r")))
                            exit(0);
                    if(!fgets(buf, sizeof(buf), fh))
                            exit(0);
                    fclose(fh);
                    if(buf[strlen(buf) - 1] == '/n')
                            buf[strlen(buf) - 1] = '/0';
                    snprintf(cmd, sizeof(cmd), "gdb %s %d -ex=bt > ./a.txt", buf, getpid());
                    system(cmd);
            
                    exit(0);
            }

            在服務(wù)器開啟時(shí),添加 signal(SIGSEGV, &dump ); 進(jìn)行信號(hào)處理掛接即可

             

             

            引用: http://blog.csdn.net/kakaka2011/article/details/6597857  作者: kakaka2011

            posted @ 2012-12-29 17:53 戰(zhàn)魂小筑 閱讀(9923) | 評(píng)論 (3)編輯 收藏

            最近為服務(wù)器添加XMLSocket與Flash進(jìn)行通信, 這種協(xié)議其實(shí)是一種以\0結(jié)尾的字符串協(xié)議, 為了讓asio兼容此協(xié)議, 我從文檔找到了async_read_until異步讀取系列, 這個(gè)函數(shù)的原理時(shí), 給定一個(gè)streambuf, 和一個(gè)分隔符, asio碰到分隔符時(shí)返回, 你可以從streambuf中讀取需要的數(shù)據(jù). 看似很簡(jiǎn)單, 我很快寫好一個(gè)demo與Flash進(jìn)行通信, 結(jié)果發(fā)現(xiàn)在一個(gè)echo邏輯速度很快時(shí), 服務(wù)器居然亂包了, 網(wǎng)上查了下, 官方原文是這樣的:

            ”After a successful async_read_until operation, the streambuf may contain additional data beyond the delimiter. An application will typically leave that data in the streambuf for a subsequent async_read_until operation to examine.”

            意思是, streambuf中并不一定是到分隔符前的所有數(shù)據(jù), 多余的數(shù)據(jù)可能一樣會(huì)在streambuf中. 也就是說, 還需要自己再次處理一遍數(shù)據(jù)...

            動(dòng)手唄, async_read_until看似就是一個(gè)廢柴, 底層已經(jīng)費(fèi)了很多CPU在逐字符與分隔符的匹配上, 拋上來的數(shù)據(jù)居然還是半成品.

            代碼如下, 測(cè)試通過, 但是實(shí)在很費(fèi)解為啥非要再做一次..

                      boost::asio::streambuf* SB = SBP.get();
            
                        // 訪問緩沖
                        const char* Buffs = boost::asio::buffer_cast<const char*>( SB->data() );
            
                        uint32 DataSize = 0;
                        for ( uint32 i = 0; i < SB->size(); ++i )
                        {
                            const char DChar = Buffs[i];
            
                            // 這里需要自己判斷字符串內(nèi)容, read_until的文檔里這么說的
                            if ( DChar == '\0' )
                            {
                                DataSize = i;
                                break;
                            }
                        }
            
                        if ( DataSize > 0 )
                        {
                            // 取成字符串
                            std::string FullText( Buffs, DataSize );
                            
                            // 消費(fèi)
                            SB->consume( DataSize );                
            
                            mWorkService->post(
                                boost::bind(&AsioSession::NotifyReadString,
                                shared_from_this(),
                                FullText )
                                );
            
                        }
              另外, 為了保證輸入性安全, 可以在streambuf構(gòu)造時(shí)加一個(gè)最大一個(gè)讀取量, 超過此量會(huì)返回報(bào)錯(cuò), 避免了緩沖區(qū)被撐爆的危險(xiǎn)
            posted @ 2012-12-03 15:12 戰(zhàn)魂小筑 閱讀(11625) | 評(píng)論 (5)編輯 收藏

            即便使用了Google SSL加密搜索, 由于Google需要對(duì)搜索結(jié)果進(jìn)行點(diǎn)擊跟蹤,因此很容易被GFW重置連接. 使用以下方法可以避免此問題

            在Chrome瀏覽器中輸入chrome://net-internals/

            在HSTS標(biāo)簽中輸入www.google.com

            點(diǎn)擊add添加即可

            posted @ 2012-09-17 23:22 戰(zhàn)魂小筑 閱讀(774) | 評(píng)論 (0)編輯 收藏

            網(wǎng)上找了很多, 真正好用的代碼不多, 自己研究了下,寫下例子備份

             

            Private Sub ConvFile(InputFile As String, OutputFile As String)
             
                Dim ReadStream As Object
                Set ReadStream = CreateObject("ADODB.Stream")
                
                Dim FileContent As String
                
                With ReadStream
                    .Type = 2               'adTypeText
                    .Charset = "UNICODE"
                    .Open
                    .LoadFromFile InputFile
                    FileContent = .ReadText
                    .Close
                    
                End With
                
                Set ReadStream = Nothing
                
                
                
                Dim WriteStream As Object
                Set WriteStream = CreateObject("ADODB.Stream")
                   
                
                With WriteStream
                    .Type = 2               'adTypeText
                    .Charset = "UTF-8"
                    .Open
                    .WriteText FileContent
                    .SaveToFile OutputFile, 2  'adSaveCreateOverWrite
                    
                    .Flush
                    .Close
                    
                End With
                
                Set WriteStream = Nothing
             
                
            End Sub

             

            上半截是讀取文件, 下半截是寫入文件, 需要轉(zhuǎn)換不同格式, 請(qǐng)自行更換

            posted @ 2012-09-13 19:43 戰(zhàn)魂小筑 閱讀(8656) | 評(píng)論 (2)編輯 收藏

            僅列出標(biāo)題
            共26頁: First 4 5 6 7 8 9 10 11 12 Last 
            国产精品久久久久AV福利动漫| 亚洲综合伊人久久大杳蕉| 久久99国产精品久久久| 激情综合色综合久久综合| 久久天天躁狠狠躁夜夜av浪潮| 国产精品乱码久久久久久软件| 日本欧美久久久久免费播放网| 一本大道久久a久久精品综合| 人人狠狠综合久久亚洲高清| 色欲久久久天天天综合网精品| 人人狠狠综合久久亚洲88| 亚洲欧洲久久av| 国产91色综合久久免费| 久久国内免费视频| 亚洲一本综合久久| 午夜精品久久久久久99热| 日本精品久久久久中文字幕| 久久香蕉一级毛片| 久久精品无码免费不卡| 国产成人久久久精品二区三区| 亚洲AV无码一区东京热久久| 久久久久久亚洲Av无码精品专口| 97久久精品人人做人人爽| 欧美精品久久久久久久自慰| 性做久久久久久久久| 成人精品一区二区久久久| 久久久av波多野一区二区| 99久久精品免费看国产一区二区三区| 国内精品久久久久国产盗摄| 久久最新精品国产| www.久久精品| AV无码久久久久不卡蜜桃| 青草国产精品久久久久久| 久久精品aⅴ无码中文字字幕不卡| 久久天天躁狠狠躁夜夜不卡 | 亚洲国产成人久久综合一| 亚洲色大成网站www久久九| 色播久久人人爽人人爽人人片AV| 久久青青草原精品国产软件| 久久久久无码精品| 精品久久久久久久久免费影院|