小记最近踩得两个C++坑
小记最近踩得两个C++坑
记一下最近踩得两个C++独有的暗坑,其中一个和ABI相关。第二个坑其实之前研究过,但是没有实例,这次算是碰到了个典型的实例。
坑一:常量引用失效
在项目中碰到的实例的大致流程是:
- 获取某个容易的迭代器,迭代器内包含智能指针(std::shared_ptr)
- 把智能指针通过常量引用方式传入函数
- 执行过程中智能指针被释放
- 于是这时候,我们有了一个空悬的智能指针引用了
用代码表示的话,流程如下:
记一下最近踩得两个C++独有的暗坑,其中一个和ABI相关。第二个坑其实之前研究过,但是没有实例,这次算是碰到了个典型的实例。
在项目中碰到的实例的大致流程是:
用代码表示的话,流程如下:
现在Redis的集群功能已经Release。但是并没有一个官方直接提供的高可用性的API可以使用。有的只有解决方案,Sentinel和Cluster。所以有必要自己设计一套高可用的Driver层以供业务使用。
之前有搜集过一些常用的命令脚本,其中有vim的部分。但是vim内置的很多功能那些个命令显然是不够的,而且那些记录的很多也不常用,于是想到专门开一个页面记录vim常用的命令集。
见 https://github.com/owent-utils/vim
/ # 向下搜索
? # 向上搜索
v # 进入可视化模式
Ctrl+v # 列编辑模式
Shift+i # 多列插入
d[d/w] # 剪切[行/单词]
y[y/w] # 复制[行/单词]
=[=] # 自动缩进[行]
p # (查看模式)粘贴
u # Undo
Ctrl+r # (查看模式)Redo
Ctrl+r Ctrl+" # (命令行模式/编辑模式)粘贴
:e # 更新缓冲区 # 和正则表达式不同的的一个地方在于,用于全字匹配的\b在vim里是 \<\>
:s/src/dst/ # 文本替换(当前行第一个src替换为dst)
:s/src/dst/g # 文本替换(当前行所有src替换为dst)
:%s/src/dst/g # 文本替换(所有行第一个src替换为dst)
:%s/src/dst/g # 文本替换(所有行所有src替换为dst)
:n,$s/ # 从第n行到结尾,类似正则表达式
:%s/ # 全文搜索
*/# # 在当前文件中搜索当前光标的单词:tabnew # 新tab打开
g(t/T) # (下/上)一个tab
:He[!] # 上[下]分屏浏览
:Ve[!] # 左[右]分屏浏览
Ctrl+w Ctrl+w # 分屏切换
:set scb[!] # 开启[关闭]分屏同步移动
:(s/v)plit # (水平/垂直)分屏打开:e . # 打开目录
:E # 目录导航
:ls # 列举缓冲区
N Ctrl+^ # 切换缓冲区Ctrl+N # 向下查找关键字关键字[插入模式下], Ctrl+P 向上查找关键字[插入模式下]
Ctrl + X 和 Ctrl + D # 宏定义补齐
Ctrl + X 和 Ctrl + ] # 是 Tag 补齐
Ctrl + X 和 Ctrl + F # 是文件名补齐
Ctrl + X 和 Ctrl + I # 也是关键词补齐,但是关键后会有个文件名,告诉你这个关键词在哪个文件中
Ctrl + X 和 Ctrl +V # 是表达式补齐
Ctrl + X 和 Ctrl +L # 对整行补齐。:%!python -m json.tool # jsom 格式化
:%!xxd[ -r] # 转入[转出]为16进制查看
gg=G # 全文自动缩进
:set encoding=utf8 # 设置显示编码
:set fileencoding=utf-8 # 文件编码转换
:help encoding-values # 列举支持得编码
:setl ff=[dos/unix/mac] # 行尾格式转换CentOS 7 已经用firewalld替换掉了iptables并用systemd来管理启动服务(之前是chkconfig)。而且下一个Ubuntu的长期支持版也要这么干了。
这两个工具在操作上和之前的系统有很多的变化,所以集中记录一下常用的命令,以免每次都要靠搜索引擎。
搭建自动化构建(jenkins)的过程中碰到了挺多问题,需要装各种插件解决。为了方便下次部署,这里先记录一下用到的插件及用途
Written with StackEdit.
最近一个人搞后台,框架底层+逻辑功能茫茫多,扛得比较辛苦,一直没抽出空来写点东西。
空闲的时间,完善了LLVM+Clang+libc++和libc++abi的编译脚本。不得不说clang的编译脚本质量比gcc差不是一点点。为了在centos下尽可能编译出更多的功能和llvm的子项目,要各种改各种试才终于自举通过,并且这种情况编出来的二进制大得夸张。不过总算是告一段落。
因为项目需要,买了本《Redis的设计与实现》的电子版,顺便给这本书的作者贡献了一丢丢的Redis文档的翻译。这本书通篇贴代码,有点看blog的感觉,写得还是很简单易懂的。(不过谁告诉我为毛我花了30大洋买完不到半个月就变成10块了,坑爹么不是。T_T)
另外还零零散散地看了些《程序员的自我修养-链接、装载与库》 这本书云风之前推荐过。并且在我看得这些里国人写得书里,这确实是一本值得推荐,并且不可多得的佳作。
还是回到正题
早先我们用得都是tolua++,但是tolua++貌似很久没有更新了,而且不支持lua大于5.1的版本。并且在使用的过程中发现了一些坑,比较隐晦+恶心。总不能让所有人时时刻刻记住这些坑吧?再加上服务器的lua脚本会比较轻量级,索性就用一个简单高效的Lua绑定机制。
LLVM和Clang工具链的生成配置文件写得比较搓,所以略微麻烦,另外这个脚本没有经过多环境测试,不保证在其他Linux发行版里正常使用。
由于生成动态库会出现一些问题,所以目前都是采用llvm默认的静态链接的方式。但是静态链接生成的文件比较大,并且链接的东西很多,有可能会出现链接超时的错误。 这时候可以通过手动cd到编译目录,执行 make && make install 即可
例行回顾一下2014年学习和看到的技术、思路、方案总结:
总的来说,2014年感觉看得东西都更加深入一些,量少一些。今年没看多少书,大致浏览了下《C++ Primer 第五版》,精读了《深度探索C++对象模型 》,第一遍过了一下《Unix环境高级编程》这本书看一遍果断是不能完全理解的,我看完第一遍的感觉最模糊的地方是终端控制那一块。还有看了一点点的《Linux内核设计艺术》果然如gaccob所说,看起来没什么意思,有点教科书的感觉。其他的零零散散的也没什么意思的书也有,比如一个讲类似libevent的事件框架的,一个讲libuv框架的,等等。目前正在抽时间精读《程序员的自我修养—链接、装载与库》,这确实算是国人写得不多得的好书哇。
本来看到Android的ndk都开始用gcc4.8和gcc4.9了,而且gcc4.8.1开始支持全部的c++11的特性,我就很happy地用上了。结果出现这么个错误。
网上查到说是Android的run time竟然不支持 thread local storage(TLS),更准确地说,是它没实现。
介于配置gitlab邮箱测试起来补交麻烦而且看日志还不明朗,这里记录一下成功配置好的企业邮箱方案。
模板如下:
# mail config
gitlab_rails['smtp_enable'] = true
gitlab_rails['smtp_address'] = "smtp.exmail.qq.com"
gitlab_rails['smtp_port'] = 465
gitlab_rails['smtp_user_name'] = "完整邮件账户"
gitlab_rails['smtp_password'] = "密码"
gitlab_rails['smtp_domain'] = "邮件账户所在域"
gitlab_rails['smtp_authentication'] = "login"
gitlab_rails['smtp_enable_starttls_auto'] = true
gitlab_rails['smtp_tls'] = true # 这个很重要,而且是官方文档里没提及的
# If your SMTP server does not like the default 'From: gitlab@localhost' you
# # can change the 'From' with this setting.
gitlab_rails['gitlab_email_from'] = '完整邮件账户'比如我的邮箱admin@owent.net
配置如下:
# mail config
gitlab_rails['smtp_enable'] = true
gitlab_rails['smtp_address'] = "smtp.exmail.qq.com"
gitlab_rails['smtp_port'] = 465
gitlab_rails['smtp_user_name'] = "admin@owent.net"
gitlab_rails['smtp_password'] = "admin@owent.net的密码"
gitlab_rails['smtp_domain'] = "owent.net"
gitlab_rails['smtp_authentication'] = "login"
gitlab_rails['smtp_enable_starttls_auto'] = true
gitlab_rails['smtp_tls'] = true
# If your SMTP server does not like the default 'From: gitlab@localhost' you
# # can change the 'From' with this setting.
gitlab_rails['gitlab_email_from'] = 'admin@owent.net'done.
本来想参考下tolua++的对象生命周期维护方式。一不小心发现了一个坑。
我这里用得是tolua++ 1.0.93版本。
tolua++在new一个类的时候,会把类指针作为userdata传入lua,建立metatable并通过tolua_classevents函数给metatable注册魔术方法。
github是程序员经常上的网站,但如果是在一家苦逼不能访问外网的公司,那不能把自己的代码托管在github上绝对是一件非常痛苦的事情。如 果想要在公司内网也可以用github托管自己的代码,那就要自己搭建类似github的服务器,好在类似github的框架有很多,基本上都是基于 git的,可以无缝衔接github而无需额外学习其他技术。
近期倒腾下客户端,想搞个cocos2d的工具。 之前的那个集成到Win32工具下的调试辅助工具是直接用的windows api。拓展起来巨麻烦。而且Windows默认的字符集是宽字符集,和cocos2d与lua交互起来得到utf-8之间转来转去,十分麻烦。所以干脆花点时间一口气搞完这货。
最近给公司搭建Gitlab作源代码管理工具 满满都是坑呐。
Gitlab 开源仓库软件包官方地址: https://about.gitlab.com/
https://about.gitlab.com/downloads/ 这里有各个Linux分支的安装包,下面的说明笔记齐全,直接使用比较简单。
我的安装环境是 CentOS 7.0 x86_64 目测Gitlab包会把自己安装在 /opt/gitlab 下,然后/usr/bin/gitlab-的几个文件软链接到/opt/gitlab/bin/gitlab-,释放初始配置到/etc/gitlab目录 执行 gitlab-ctl reconfigure之后,在/var/opt/gitlab 下保存配置和数据
LLVM和Clang工具链的生成配置文件写得比较搓,所以略微麻烦,另外这个脚本没有经过多环境测试,不保证在其他Linux发行版里正常使用。
如果第一次执行出现安装失败,可以再执行一次。llvm的安装脚本问题多多
接上文
虽然我很不愿意再设计一套BUS系统,但是现有的一些确实都没有特别符合我的口味的。所以还是尝试设计一个出来。
简单来说,我希望BUS系统可以简单、高效、稳定。
首先,在节点标识方面,类似ZeroMQ的用字符串来标识端点的做法我认为是不必要的。这点上可以参照前面两种的设计,但某些情况下32位作类型分割的可能会不够,所以可以使用64位标识。其实还有一个重要的原因是64位数字可以整个存放在CPU寄存器里,可以通过一个汇编指令进行比较操作,无论性能还是可以表示的节点个数都很足够。
如何保证一个进程或线程能安全稳定地把一段消息发送到另一个进程和线程,甚至是另一台机器的进程或线程,再或是要通过代理转发到另一个进程或线程,一直是一个比较麻烦的问题。
最近看了一些和BUS系统有关的东西。对于游戏服务器集群所使用的BUS通信系统有一些想法和思路,但是由于我对其他类型的业务和框架不是很熟悉,有些想法可能仅是站在游戏服务端的立场上,所以可能有些地方还有一些局限性。
Github地址: https://github.com/owent/libiniloader
OSChina镜像: http://git.oschina.net/owent/libiniloader
项目中经常会碰到需要读取配置的情况,而用ini配置最大的优势就是简单易懂。 但是现在很多的配置读取库都过于庞大了,比如Boost.PropertyTree,功能很强大,但是基本不会用到里面所有的东西。 另外微软的INI读取,功能不是很强不说,还限制在Windows上,更重要的是API设计得实在不优雅。 于是libiniloader就诞生啦。