• Geek_1b6d74
    2021-10-13
    陈天大神太强了,学习他的课程不仅学习了一门新的语言,还弄明白了很多编程底层原理

    作者回复: 过奖了!:)

    
    14
  • 核桃
    2021-11-20
    老师,专门开一期如何读开源项目源码吧,真的,这个比懂任何技巧都更有意义,目前也没有教这个的。

    作者回复: :) 掌握好这一章就好了啊

    
    6
  • 枸杞红茶
    2021-10-31
    我原本准备去超市摸鱼,陈天老师给我渔船把我扔到了大海里

    作者回复: 哈哈,放下你泡好枸杞红茶的保温杯,一起死磕 Rust :)

    
    4
  • Marvichov
    2021-11-08
    1. 我们一起大致分析了 Bytes 的 clone() 的使用的场景,你能用类似的方式研究一下 drop() 是怎么工作的么? 如果是Shared, 就像Arc那样decrease counter; 如果是KIND_VEC, with unique ownership, deallocate memory immediately. unsafe fn promotable_odd_drop(data: &mut AtomicPtr<()>, ptr: *const u8, len: usize) { data.with_mut(|shared| { let shared = *shared; let kind = shared as usize & KIND_MASK; if kind == KIND_ARC { release_shared(shared as *mut Shared); } else { debug_assert_eq!(kind, KIND_VEC); drop(rebuild_boxed_slice(shared as *mut u8, ptr, len)); } }); } 2. 仔细看 Buf trait 里的方法,想想为什么它为 &mut T 实现了 Buf trait,但没有为 &T 实现 Buf trait 呢?如果你认为你找到了答案,再想想为什么它可以为 &[u8] 实现 Buf trait 呢? 因为advance method需要更改T内部状态 fn advance(&mut self, cnt: usize) { 3. 花点时间看看 BufMut trait 的文档。Vec 可以使用 BufMut 么?如果可以,试着写写代码在 Vec 上调用 BufMut 的各种接口,感受一下。 只能在`Vec<u8>` 上用; 跟着doc试了一下. 值得注意的是, `advance_mut`是 `unsafe`: #[inline] unsafe fn advance_mut(&mut self, cnt: usize) { let len = self.len(); let remaining = self.capacity() - len; assert!( cnt <= remaining, "cannot advance past `remaining_mut`: {:?} <= {:?}", cnt, remaining ); self.set_len(len + cnt); } 4. 如果有余力,可以研究一下 BytesMut。重点看一下 split_off() 方法是如何实现的。 `split_off` 也是根据kind来: - 如果是KIND_VEC, 就变成两个Arc, 共享同一个buf pointer - 如果是KIND_ARC, 就increase ref count, 设置不同的start, end 感觉真正困难的是 `reserve` 和 `resize`; 这两个method要求KIND_ARC; 这样, 所有outgoing的`BytesMut` 能view underlying Vec pointer change during reallocation
    展开

    作者回复: 👍

    
    2
  • Geek2014
    2021-10-08
    而 data 这个 AtomicPtr 指针,在指向 Shared 结构时,这个结构的对齐是 2/4/8 字节(16/32/64 位 CPU 下),末尾一定不为 0: 老师,为啥对齐2/4/8字节,末尾一定不为0呢

    作者回复: 啊,多谢发现!这里是笔误,应该是一定为 0。为 0 才可以借用最后一位设置是否是 shared 标志。这是上下文的逻辑。我让编辑更新一下。

    
    2
  • Geek_b52974
    2021-11-05
    看後面的解釋還是有點懵,我試著照自己的理解說明 最後一位是用來記錄是否是 shared 但是我們會需要知道升級成 shared 前最後一位是 odd 還是 event 所以用 PROMOTABLE_ODD_VTABLE PROMOTABLE_EVENT_VTABLE 來做不同的 clone 方式 ``` unsafe fn promotable_even_clone(data: &AtomicPtr<()>, ptr: *const u8, len: usize) -> Bytes { let shared = data.load(Ordering::Acquire); let kind = shared as usize & KIND_MASK; if kind == KIND_ARC { shallow_clone_arc(shared as _, ptr, len) } else { debug_assert_eq!(kind, KIND_VEC); let buf = (shared as usize & !KIND_MASK) as *mut u8; shallow_clone_vec(data, shared, buf, ptr, len) } } ``` promotable_event_clone 相比 promotable_odd_clone 多了下面這個操作 let buf = (shared as usize & !KIND_MASK) as *mut u8; 先把最後一位還原成原本的樣子,再進行 clone 不知道這樣理解對不對
    展开

    作者回复: 对

    
    1
  • 25ma
    2022-07-08
    值得反复深度阅读,很有收获

    编辑回复: 👍

    
    
  • 施泰博
    2021-12-18
    看完我觉得值得,得反复看很多编了。

    作者回复: 👍

    
    
  • overheat
    2021-12-10
    Bytes可以支持反序吗?我想要从结尾往开头操作。。。

    作者回复: 不支持,你需要先做 reverse 的操作

    共 3 条评论
    
  • 小康
    2021-11-13
    老师,目前中国rust岗位很多都是区块链相关的技术岗位呀???java转Rust跨度会不会太大???

    作者回复: 1. 目前是,以后基础软件会有越来越多的 Rust 职位 2. 不会

    
    