分类
Rust

rust static lifetime

Note that the error message talks about the argument type outliving the 'static lifetime. This terminology can be rather confusing because the 'static lifetime lasts until the end of the program, so if it outlives it, don’t you have a memory leak? The explanation is that it is the type, not the value that must outlive the 'static lifetime, and the value may be destroyed before its type is no longer valid.

分类
others

使用 github API 删除库

首先,在 https://github.com/settings/tokens 设置 Personal access tokens

1 使用Token测试一下,获取个人信息

curl -i -u qjanda:ghp_4FILog9ho4TpWf7noYrUmDUNqir5v819NHfe https://api.github.com/user

2 使用delete repository;

curl -u qjanda:ghp_4FILog9ho4TpWf7noYrUmDUNqir5v819NHfe   -X DELETE -H “Accept: application/vnd.github.v3+json”   https://api.github.com/repos/epmpub/SimpleWebAPI

分类
C++

C/C++ Sanitizer 简介


Sanitizer 英文翻译过来是杀菌剂的意思,Google 提供了很多相关的一些 Sanitizers ,用来检测程序的异常。

可以做内存、地址访问、竞态条件的检测,这里简单介绍。

简介

目前有 AddressSanitizer MemorySanitizer ThreadSanitizer LeakSanitizer 几种,不同的编译工具版本,所支持的特性可能有所区别。

安装

在 CentOS 中需要安装 libasan (AddressSanitizer)、libtsan (ThreadSanitizer) 库。

ThreadSanitizer

又被称为 TSan,是一个检查线程 Data Race 的 C/C++ 工具,集成在新版的 gcc/clang 中,在编译时可以通过添加 -fsanitize=thread 参数,那么在运行时会检测出 Data Race 的问题。

所谓的竞态的条件是指,多个线程同时访问相同的变量,而且其中有一个变量会尝试写入。

示例

#include <stdio.h>
#include <pthread.h>

int Global;

void *Thread1(void *x)
{
        Global++;
        return NULL;
}

void *Thread2(void *x)
{
        Global--;
        return NULL;
}

int main(void)
{
        pthread_t t[2];
        pthread_create(&t[0], NULL, Thread1, NULL);
        pthread_create(&t[1], NULL, Thread2, NULL);
        pthread_join(t[0], NULL);
        pthread_join(t[1], NULL);
}

然后通过 gcc -fsanitize=thread -fPIE -pie -g race.c -o race 编译,运行的输出结果如下。

==================
WARNING: ThreadSanitizer: data race (pid=24693)
  Read of size 4 at 0x564178840078 by thread T2:
    #0 Thread2 /tmp/main.c:14 (a.out+0x000000000aaf)
    #1 <null> <null> (libtsan.so.0+0x00000002583b)

  Previous write of size 4 at 0x564178840078 by thread T1:
    #0 Thread1 /tmp/main.c:8 (a.out+0x000000000a6a)
    #1 <null> <null> (libtsan.so.0+0x00000002583b)

  Location is global 'Global' of size 4 at 0x564178840078 (a.out+0x000000201078)

  Thread T2 (tid=24696, running) created by main thread at:
    #0 pthread_create <null> (libtsan.so.0+0x000000028e53)
    #1 main /tmp/main.c:22 (a.out+0x000000000b39)

  Thread T1 (tid=24695, finished) created by main thread at:
    #0 pthread_create <null> (libtsan.so.0+0x000000028e53)
    #1 main /tmp/main.c:21 (a.out+0x000000000b18)

SUMMARY: ThreadSanitizer: data race /tmp/main.c:14 in Thread2
==================
ThreadSanitizer: reported 1 warnings

上述信息显示了在代码的那些地方出错。

需要注意的是:

  • 除了加 -fsanitize=thread 外,一定要加 -fPIE -pie 否则编译报错。
  • 通过 -g 参数方便显示文件名和行号。
  • 如果生成二进制分了编译连接,那么每步都要添加上述参数,并在连接时添加 -ltsan 。
  • 如果依赖其它静态库,则这些静态库编译时必须指定 -fPIC 。

实现原理

如果要实现一个竞态条件检测,需要满足如下两点:

  1. 知道哪些线程在访问那个内存空间;
  2. 知道是否未做同步而直接访问。

在 V2 版本里,是基于 Shadow Memory 机制来实现的,相比来说其效率要更高。

所谓的 Shadow Memory 实际上是原程序内存的镜像,会记录那个线程访问过,以及何时访问的。

在开启了竞态检测之后,会将部分代码插入到原程序中,然后会初始化并维护 Shadow Memory 的内容,这也就是为什么需要依赖 libtsan 动态库。

接下来,看看其如何解决上面提到的两个问题。

参考

引用:https://gohalo.me/post/language-c-some-sanitizers-introduce.html

分类
C++

std::iota的用法

std::iota :用顺序递增的值赋值指定范围内的元素 。

函数声明:

// <numeric>
template< class ForwardIterator, class T >
void iota( ForwardIterator first,ForwardIterator last, T value );

该函数等价于:

template<class _FwdIt,class _Ty> inline
    void _Iota(_FwdIt _First, _FwdIt _Last, _Ty _Val)
{   // compute increasing sequence into [_First, _Last)
    for (; _First != _Last; ++_First, ++_Val)
        *_First = _Val;
}

参数:

  • first,last:
    分别指向序列中初始及末尾位置的正向迭代器(Forward Iterators)。这个范围即 [first,last) ,包括 first 到 last 间的所有元素,包括 first 指向的元素,但不包括 last 指向的元素。
  • val:用于累加的初始值。
#include <iostream>
#include <numeric>
#include <iterator>
#include <vector>
namespace ClassFoo
{
    void Iota_1() 
    {     
        std::vector<int> foo;// 构造一个 vector 对象
        foo.resize(15);        
        std::iota(foo.begin(), foo.end(), 9);
// 将从 9 开始的 15 次递增值赋值给 foo
        // 输出 foo 中的内容
        std::copy(foo.begin(),foo.end(),std::ostream_iterator<int>(std::cout, " "));
        std::cout << std::endl;
    }
}
int main()
{
    ClassFoo::Iota_1();
    return 0;
}
//输出结果:9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 

分类
C++

C++ Blog资源

现整理收集C++世界里那些“牛人”的个人博客。凡三类:一是令人高山仰止的大牛,对C++语言本身产生过深远的影响的人;二是C++运用炉火纯青的高手,有原创性的技术干货;三是中文世界里的C++牛人。

C++大牛的博客

Bjarne Stroustrup,不认识的可以去面壁了,没有他,就没有我们现在的饭碗。Bjarne Stroustrup是丹麦人,目前任教于TAMU。他的Homepage和他的书籍《The C++ Programming Language》一样,都是百科全书级的,如果你认真研究,你也会成为你同事或周围人的C++之父。

Scott Meyers,不多介绍,世界上几乎每个C++程序员都应该知道的名字,畅销书:《Effective C++》《More Effective C++》的作者。博客长期更新,就凭Scott Meyers这个名字,就值得一读。

Lippman,C++第一个编译器Cfront的实现者,最大的贡献是凭借其著作《C++ Primer》在世界范围内普及了C++。Lippman本人算是个励志故事,父母是蓝领移民,他为了融入美国主流社会而努力工作,终于取得了今日的成就,他的另一本书《inside The C++ Object Model》让我知道了C++代码编译后的样子,不过我不知他写该书时发生了什么事情,因为书中有大量的低级错误,与前一本书的严谨截然相反。列出他的博客,更多的是因为他是C++牛人中无法绕过的一个,而其博客久不更新,早已荒芜,而且是MSDN上的专栏,可能不太能提起人多大兴趣去读。

Herb Sutter, C++标准委员会主席,目前就职于微软。代表作为C++ Exceptional系列:《Exceptional C++》《More Exceptional C++》《Exceptional C++ Style》, 因封面头像蓄须,被国人称“小胡子”,不过貌似现在刮干净了。博客更新很快,内容杂乱,有技术亦有资讯,gotw系列个人感觉不错。

Andrei Alexandrescu,罗马尼亚人,目前任职于FaceBook, C++天书《Modern C++ Design: Generic Programming and Design Patterns Applied》的作者,凭借此书使C++社区认识到模板编程鬼斧神工之力。后来不满C++而转投D语言,是D语言的主要开发者。不过他的博客貌似好久不更新了,内容也大多学术气息浓厚。

David Abrahams,美国人,C++标准委员会成员,将exception-safety加入标准,Boost.org的联合创始人,《C++ Template Metaprogramming》的作者。但博客内容一般,最后一篇内容更新时间是12年的,内容不多,也没有太多亮点,不过笑容却是感染了我。

Bartosz Milewski,波兰人,物理系毕业的计算机大牛,曾就职于微软。《c++ in action》的作者。博客更新频繁,内容密实,观点前卫,对C++的不满流露于字里行间,多以Haskell对比C++的不足,然后实现一些函数式编程风格的C++代码。

不才曾翻译过他的文章:C++手爱德华

Anthony Williams,英国人,一个记事起就开始写程序的人。Boost.Thread的作者,参与了C++11 Thread的标准化工作。博客有一部分技术文章,也有一些标准化和他自己维护的一些库的记录,对C++多线程感兴趣的可以读一下他的书:《C++ Concurrency in Action》,市面上第一本讲解C++11并发的权威书籍。

Alexander A. Stepanov,出生于莫斯科,STL之父,《编程原本》的作者。Alexander A. Stepanov的这个博客如其名,是他个人学术论文的整理,学术价值应该是蛮高吧,不过像我这种低级程序员只能远观了。

Matt Austern, 现任职于Google, 前C++标准委员会主席,SCG STL的最初实现者,《Generic Programming and the STL》的作者。Matt Austern的这个博客其实是个人主页,没有太多技术东西,只是一些生平和生活照片,无聊的看一下倒还行。

P.J. Plauger,这个名字可能不是每个人都听说过,但在Windows平台开发的同学肯定都用过他写的代码,他就是MS VC STL库的实现者。本来他的博客,只是个人主页并且上面没什么内容,不过看到他的履历里面完成了13部科幻小说的编写,拿来勉励大家吧。

##C++高手的博客

Andrzej Krzemieński,从名字看是波兰人,近期博客更新较快,表达清晰,行文流畅,内容难度不高,有C++11内容,是像我这样的初级并且语言控的C++程序员的福音。

Sumant Tambe,印度人,美国范德堡大学的计算机博士,技术涉猎广泛,同时也是著名的More C++ Idioms创建者。博客一直更新,内容面向中高级C++程序员,最新文章涉及C++11的“高级Idioms”,比如13年10月的一篇文章主题是:创建递归的lambda表达式。

Jeff Preshing,加拿大人,自称游戏行业开发10数年,C++功力自是深厚。博客每年更新十数篇,C++相关文章内容上进,直面工程上的难题:并发,而不是在C++本身上打转转。且行为流畅,图文并茂,深入浅出,是C++工程控的福音。

Joaquín M López Muñoz,西班牙人。Boost.MultiIndex的实现者。博客长期更新,内容偏向算法,文章中有大量的公式推演和曲线图表,估计大部分中国开发者对这种内容是不感冒的。计算机或数学系的研究生,并以后打算从事算法相关工作的,推荐阅读。从这个西班牙男人身上,也可以看到老牌欧洲资本主义国家,教育水平的强悍,尤其是基础学科。

Daniel Park,喜欢用昵称whanhee,身世不知。一个注重实干的C++狂热分子,正如其博客简介所说,不想接着讲那些被讲烂掉的函数式编程概念,要用C++来实现这些概念。博客是一个关于函数式编程概念如何用C++实现的一个系列文章,作者采用的是C++11乃至C++14的特性,所以对C++高级函数式实现思想感兴趣的不容错过。近期博客更新也较快的。

Agustín Bergé,86年生阿根廷人,可能是这里面最年轻的,stackoverflow目前排名708。作者想用自己的博客探索永无边界的C++世界,尤其是那些前人未涉足的犄角旮旯,所以C++中毒颇深者可以看看。

Chris Kohlhoff,澳大利亚人,Boost.asio作者。博客更新到10年,内容主要涉及网络,asio相关,使用asio的可以去看看。

中文C++名博

刘未鹏,84年生人,现就职于微软,《Imperfect C++》《Exceptional C++ Style》译者,大学时对C++有极大的学习兴趣,曾与C++之父邮件往来,记录在另一个博客C++的卢浮宫上。据闻刘未鹏现忙于育儿与心理学,所以博客更新较慢,但以往博客含金量高,很值得一读。博客内容偏重于学习方法,纯技术的C++文章少些。

陈皓,不认为自己是牛人的牛人,现就职于阿里巴巴。程序员技术练级攻略这篇博文足以奠定其江湖地位。陈皓自称有技术焦虑症,所以博客更新频繁,内容大量涉及C++及一切劝人上进的观点和方法,也有不少网友的高质量投稿,涉及软件开发的方方面面。

陈硕,国内少有的C++工程功底深厚,作风严谨且乐于分享的人。Muduo开源库的作者,有干货著作《Linux多线程服务端编程:使用muduo C++网络库》一本,译注若干。

引用自这里

分类
C++

C++ Top 10 Resource

https://wg21.link/

https://isocpp.org

https://leanpub.com/

https://eel.is/c++draft

https://reddit.com/r/cpp

https://www.fluentcpp.com/

https://www.cppstories.com/

https://randomascii.wordpress.com/

https://www.modernescpp.com/index.php/rainer-grimm

https://devblogs.microsoft.com/oldnewthing/20210412-00/?p=105078