curl在Android系统卡死的问题

问题描述:
调用 curl 获取消息头的时候,发现程序卡住不动了。代码如下:

curl_easy_setopt(curl, CURLOPT_URL, srcUrl.c_str());
curl_easy_setopt(curl, CURLOPT_HEADER, 1);
curl_easy_setopt(curl, CURLOPT_NOBODY, 1);
curl_easy_perform(curl); // 这句直接卡死,没有任何返回

经测试发现,不做任何设置,做一次发送,同样会卡死。

curl_easy_setopt(curl, CURLOPT_URL, srcUrl.c_str()); 
curl_easy_perform(curl); // 这句直接卡死,没有任何返回

解决方案:

经过反复试验,在请求的时候设置写数据回调,就可以正常执行了。

void size_t writeFunc(void *ptr, size_t size, size_t nmemb, void *userdata)
{
    return 0;
}
curl_easy_setopt(curl, CURLOPT_URL, srcUrl.c_str());
curl_easy_setopt(curl, CURLOPT_HEADER, 1);
curl_easy_setopt(curl, CURLOPT_NOBODY, 1);
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, writeFunc);
curl_easy_setopt(curl, CURLOPT_WRITEDATA, nullptr);
curl_easy_perform(curl);

具体原因不详,暂时没有精力去读它的代码。我猜卡死的问题与代码本身关系不大,暂时比较怀疑编译库的工具链。由于之前遇到过 ndk 编译出的 sscanf 等函数调用卡死,所以这货暂时列为A级怀疑对象。

C++ 如何让自己的类支持foreach

首先,我们先看看使用 foreach 的时候,都发生了什么。

新建一个类,根据经验,我们 for 一个对象应该是这样的:
for (XX::iterator iter = xx.begin(); iter != xx.end(); ++iter)
所以,迭代器, beigin(), end() 应该是会用得到的,我们做个试验:
Generator.h
class Generator 
{
public:
    typedef int *iterator;
    iterator begin();
    iterator end();
};

Generator.cpp

Generator::iterator Generator::begin()
{
    std::cout << "begin()" << std::endl;
    return nullptr;
}

Generator::iterator Generator::end()
{
    std::cout << "end()" << std::endl;
    return nullptr;
}
main.cpp
Generator g;
for (auto i: g)
{
    std::cout << i << std::endl;
}
运行结果:
begin() 
end()
说明我们想的没错,foreach 跟上边的 for 的行为是一样的。
插个体外话,(发现字打错了,不过不改了,还是挺哏儿的)
1. 之前以为 for (const auto i : g) 会调用 const 版本的 cbegin cend ,然而 并不会。
2. iterator 叫什么名字都没什么所谓,起名叫 红太阳 也ok。
接下来,处理一下迭代器:(我想确认一下丫具体被如何操 做)
class iterator
{
public:
    iterator(int*p)
    : _p(p)
    {
    }
    int * operator()()
    {
        std::cout << "operator()" << std::endl;
        return _p;
    }
    int operator*()
    {
        std::cout << "openator*" << std::endl;
        return 0;
    }
    iterator & operator++()
    {
        std::cout << "++operator" << std::endl;
        ++_p;
        return *this;
    }
    iterator operator++(int)
    {
        std::cout << "operator++" << std::endl;
        return _p++;
    }
    bool operator==(const iterator& it)
    {
        std::cout<< "operator==" <<std::endl;
        return true;
    }
    bool operator!= (const iterator& it)
    {
        std::cout<< "operator!=" <<std::endl;
        return true;
    }
private:
    int *_p;
};
输出结果:
begin() 
end() 
operator!= 
openator* 
0 
++operator 
operator!= 
openator* 
0 
++operator 
operator!= 
openator* 
0

已经足够说明问题了,自己把剩下的细节补充上就好了。

总结一下要点:
1. begin() end()
2. 迭代器
3. 迭代器重载 !=
4. 迭代器重载 前++
5. 迭代器重载 *(解引用)

iOS命令行打包的坑

最近在搞自动打包的时候,不小心踩到了了烂水果没有来得及擦干净的菊花。

总结一下经验教训:
1.技术
找不到ResourceRules.plist
类似这样的警告:
Warning: –resource-rules has been deprecated in Mac OS X >= 10.10! /tmp/QYFSJIvu7W/Payload/XX.app/ResourceRules.plist: cannot read resources
经过我缜密的调(gu)查(ge)取(bai)证(du),大致上可以猜测是烂水果更新了签名机制后并没有更新整套命令行工具。
秘密就藏在……
执行以下命令:
xcrun -sdk iphoneos -f PackageApplication

定位到 PackageApplication 然后用随便什么文本编辑器打开

搜索 ResourceRules ,定位到之后,清理掉与她有关的参数,整成这样:
my @codesign_args = ("/usr/bin/codesign", "--force", "--preserve-metadata=identifier,entitlements", "--sign", $opt{sign});

就这样。

亲测有效,目前尚未发现副作用。
参考文献:(临时找来凑数的)
2.
签名验证失败:
Program /usr/bin/codesign returned 1 :
resource envelope is obsolete 这个错误
stackoverflow 上大神给出的解决方案就是在 codesign 验证的时候,加上 –no-strict (不严格验证?这尼玛确实不报错了,然而……总之就是不报错了)
具体操作方式,也是向上边一样,修改 PackageApplication
找到 —verify 那行 加上 –no-strict 参数:
my $result = runCmd("/usr/bin/codesign", "--verify", "--no-strict", "-vvvv", $plugin );

参考资料:

RSS
Follow by Email
YouTube
YouTube
Pinterest
fb-share-icon
LinkedIn
Share
VK
Weibo
WeChat
WhatsApp
Reddit
FbMessenger
Copy link
URL has been copied successfully!