文章
彻底理解 C ABI
https://zhuanlan.zhihu.com/p/692886292
今天群聊提到了一个场景,unique_ptr传值加move 并不能完美优化掉,看代码
代码语言:javascript复制
代码语言:javascript复制void consume(int* ptr);
void foo(int* ptr) {
consume(ptr);
}
foo:
jmp consume@PLT
void consume(unique_ptr<int> ptr);
void foo(unique_ptr<int> ptr) {
consume(std::move(ptr));
}
foo(std::unique_ptr<int, std::default_delete<int> >):
push rbx
sub rsp, 16
mov rax, QWORD PTR [rdi]
mov QWORD PTR [rdi], 0
lea rdi, [rsp 8]
mov QWORD PTR [rsp 8], rax
call consume(std::unique_ptr<int, std::default_delete<int> >)
mov rdi, QWORD PTR [rsp 8]
test rdi, rdi
je .L1
mov esi, 4
call operator delete(void*, unsigned long)
.L1:
add rsp, 16
pop rbx
ret
mov rbx, rax
jmp .L3
foo(std::unique_ptr<int, std::default_delete<int> >) [clone .cold]:
代码语言:javascript复制
主要原因是 函数实参在 caller 方析构, unique_ptr没有彻底优化掉。感觉可以优化掉
改成传引用,传&&甚至改成not_null都能省掉
代码语言:javascript复制void consume(not_null<int> ptr); //std::unique_ptr<int> && 也可以
void foo(not_null<int> ptr) {
consume(ptr); //
}
/*
foo(not_null<int>):
jmp consume(not_null<int>)
*/
代码语言:javascript复制
感谢anms nugine ni fvs zwuis 讨论
godbolt https://godbolt.org/z/fbqEa4M1r
noexcept
Can (Sometimes) Help (or Hurt) Performance
https://16bpp.net/blog/post/noexcept-can-sometimes-help-or-hurt-performance/
使用noexcept需要保证没有异常,否则生成的代码代价更高
通常来说noexcept是给move用的
另外有一个搞笑的场景
noexcept affects libstdc ’s unordered_set
https://quuxplusone.github.io/blog/2024/08/16/libstdcxx-noexcept-hash/
libstdc 的 unordered set 对于noexcept限定 针对hash函数有特化 如果hash函数是noexcept 认为函数计算很轻,不额外保存key hash,否则会缓存key hash加速
这就导致一个尴尬的场景,对于int,这种优化是对的,对于string hash接口使用noexcept会弄巧成拙速度更慢
标准库对于noexcept限定应该给用户端保留余地,不要影响效果,如果影响,最好给出api约定,比如transparent compare
这种莫名其妙的限制很坑,可能喜欢秀一下用noexcept正好掉坑里
libstdc 说明 在这里 https://gcc.gnu.org/onlinedocs/libstdc /manual/unordered_associative.html
Temporarily dropping a lock: The anti-lock pattern
https://devblogs.microsoft.com/oldnewthing/20240814-00/?p=110129
异步lock暂时解锁的组件。代码
代码语言:javascript复制
代码语言:javascript复制template<typename Mutex>
struct anti_lock
{
anti_lock() = default;
explicit anti_lock(Mutex& mutex)
: m_mutex(std::addressof(mutex)) {
if (m_mutex) m_mutex->unlock();
}
private:
struct anti_lock_deleter {
void operator()(Mutex* mutex) { mutex->lock(); }
};
std::unique_ptr<Mutex, anti_lock_deleter> m_mutex;
};
winrt::fire_and_forget DoSomething()
{
auto guard = std::lock_guard(m_mutex);
step1();
// All co_awaits must be under an anti-lock.
int cost = [&] {
auto anti_guard = anti_lock(m_mutex);
return co_await GetCostAsync();
}();
step2(cost);
}
代码语言:javascript复制
Surprisingly Slow NaNs
https://voithos.io/articles/surprisingly-slow-nans/
代码存在0除0导致NAN NAN导致性能下降
规避?isnan判定 DCHECK
What's so hard about class types as non-type template parameters?
https://brevzin.github.io/c /2024/08/15/cnttp/
NTTP 支持类实例的困难原因 无法判定相等
有operator template()提案和反射提案的加持下可能有解
Reflection-based JSON in C at Gigabytes per Second
https://lemire.me/blog/2024/08/13/reflection-based-json-in-c-at-gigabytes-per-second/
反射给普通库带来压倒性序列化速度, 10倍以上
反射快来吧
互动环节
上周熬夜看了街霸6比赛 直接给我看的不困了,尤其是肯打aki那场,看的我心率110,真刺激
不过熬夜的后果就是一周都缓不过来。睡眠问题非常大,累计起来了,石油杯这个比赛作息太抽象了
时间真快啊,转眼夏天就过去了我靠,感觉啥也没干
东西太多根本看不过来,时间真是不够用