賴劭芊
    • Create new note
    • Create a note from template
      • Sharing URL Link copied
      • /edit
      • View mode
        • Edit mode
        • View mode
        • Book mode
        • Slide mode
        Edit mode View mode Book mode Slide mode
      • Customize slides
      • Note Permission
      • Read
        • Only me
        • Signed-in users
        • Everyone
        Only me Signed-in users Everyone
      • Write
        • Only me
        • Signed-in users
        • Everyone
        Only me Signed-in users Everyone
      • Engagement control Commenting, Suggest edit, Emoji Reply
    • Invite by email
      Invitee

      This note has no invitees

    • Publish Note

      Share your work with the world Congratulations! 🎉 Your note is out in the world Publish Note

      Your note will be visible on your profile and discoverable by anyone.
      Your note is now live.
      This note is visible on your profile and discoverable online.
      Everyone on the web can find and read all notes of this public team.
      See published notes
      Unpublish note
      Please check the box to agree to the Community Guidelines.
      View profile
    • Commenting
      Permission
      Disabled Forbidden Owners Signed-in users Everyone
    • Enable
    • Permission
      • Forbidden
      • Owners
      • Signed-in users
      • Everyone
    • Suggest edit
      Permission
      Disabled Forbidden Owners Signed-in users Everyone
    • Enable
    • Permission
      • Forbidden
      • Owners
      • Signed-in users
    • Emoji Reply
    • Enable
    • Versions and GitHub Sync
    • Note settings
    • Note Insights
    • Engagement control
    • Transfer ownership
    • Delete this note
    • Save as template
    • Insert from template
    • Import from
      • Dropbox
      • Google Drive
      • Gist
      • Clipboard
    • Export to
      • Dropbox
      • Google Drive
      • Gist
    • Download
      • Markdown
      • HTML
      • Raw HTML
Menu Note settings Versions and GitHub Sync Note Insights Sharing URL Create Help
Create Create new note Create a note from template
Menu
Options
Engagement control Transfer ownership Delete this note
Import from
Dropbox Google Drive Gist Clipboard
Export to
Dropbox Google Drive Gist
Download
Markdown HTML Raw HTML
Back
Sharing URL Link copied
/edit
View mode
  • Edit mode
  • View mode
  • Book mode
  • Slide mode
Edit mode View mode Book mode Slide mode
Customize slides
Note Permission
Read
Only me
  • Only me
  • Signed-in users
  • Everyone
Only me Signed-in users Everyone
Write
Only me
  • Only me
  • Signed-in users
  • Everyone
Only me Signed-in users Everyone
Engagement control Commenting, Suggest edit, Emoji Reply
  • Invite by email
    Invitee

    This note has no invitees

  • Publish Note

    Share your work with the world Congratulations! 🎉 Your note is out in the world Publish Note

    Your note will be visible on your profile and discoverable by anyone.
    Your note is now live.
    This note is visible on your profile and discoverable online.
    Everyone on the web can find and read all notes of this public team.
    See published notes
    Unpublish note
    Please check the box to agree to the Community Guidelines.
    View profile
    Engagement control
    Commenting
    Permission
    Disabled Forbidden Owners Signed-in users Everyone
    Enable
    Permission
    • Forbidden
    • Owners
    • Signed-in users
    • Everyone
    Suggest edit
    Permission
    Disabled Forbidden Owners Signed-in users Everyone
    Enable
    Permission
    • Forbidden
    • Owners
    • Signed-in users
    Emoji Reply
    Enable
    Import from Dropbox Google Drive Gist Clipboard
       owned this note    owned this note      
    Published Linked with GitHub
    Subscribed
    • Any changes
      Be notified of any changes
    • Mention me
      Be notified of mention me
    • Unsubscribe
    Subscribe
    # 2016q3 Homework2 (phonebook-concurrent) contributed by <`shelly4132`> ## 開發環境 * ### 作業系統:Ubuntu 16.04 LTS * ### Cache: ```$ lscpu | grep cache``` * L1d cache:32K * L1i cache:32K * L2 cache:256K * L3 cache:3072K ## Concurrency vs. Parallelism * **Concurrency**:我們將一個程式分割成多個小部份稱為task,而concurrency就是在一個proccessor的情況下,在能保證其正確性的前提下對這些task進行並行運算(thread不一定會同時執行)。 ![](https://hackpad-attachments.s3.amazonaws.com/embedded2016.hackpad.com_K6DJ0ZtiecH_p.537916_1460613316743_p1.png) * **Parallelism**:parallelism則是指在多個proccessor的情況下,我們為了增進執行速度而對一個程式進行平行運算(同時執行多個thread)。 * ![](https://hackpad-attachments.s3.amazonaws.com/embedded2016.hackpad.com_K6DJ0ZtiecH_p.537916_1460613329719_p2.png) ## Sequenced-before sequeced-before就是一種在同一個thread下,求值順序關係的描述。 * 求值:可分為value computation(運算完的結果)和side effect(修改記憶體內變數的值、呼叫library內的I/O function等等) 1. 如果A is sequenced-before B,代表A的求值會先完成,才進行對B的求值 2. 如果A is not sequenced before B 而且 B is sequenced before A,代表B的求值會先完成,才開始對A的求值。 3. 如果A is not sequenced before B 而且 B is not sequenced before A,代表兩種可能,一種是順序不定,甚至這兩者的求值過程可能會重疊(因為CPU優化指令交錯的關係)或不重疊 雖然我們對運算優先權做了很多定義,比如說f1() + f2()會先計算完f1()和f2()才計算他們加起來的結果(運算元的運算優於運算子),但仍有許多運算是未定義的。 比如說 ``` i = i++; ```,我們不知道究竟i會等於++後的結果還是等於i目前的值,因為我們沒有定義assignment跟```i++```的side effect的先後關係,所以讓程式產生了不確定性。 ## Happens-before happens-before就是指前一個操作的效果必須在下一個操作執行之前出現。 但happens-before並不是指前一行的程式碼必須先於後一行的程式碼執行,只要執行出來的結果++看起來++像是那樣,那後面的程式碼先被執行也沒關係。 * sequence-before其實就是同一個thread裡的happens-before。 * 在多個thread的情形底下如果變數共用,若沒有保證happens-before的關係的話,可能會導致程式出現意料之外的結果。 ## Coroutines * **Context Switch**:由OS根據一定的排程演算法,讓CPU一直保持有proccess在執行,而等到要執行某個proccess才把他的資料讀進記憶體,再把部份資料移出去的動作就叫context switch。 * **Coroutines**:由programmer利用一些程式技巧延遲執行某些task,讓程式不會因為某個要執行很久的東西而停頓。 * coroutines的成本比context switch低 ## POSIX Threads * Proccess:一個 process 包括了一個執行中的程式,和一些 他所需的系統資源,諸如檔案描述表和位址空間等。 * Thread:thread 實質上就是一個程式計數器、一個堆疊再加上一組暫存器。一個proccess中可以有多個thread,而這些thread都共享同一個記憶體資源。 ### 基本用法 * 宣告一個執行緒 ```pthread_t a_thread;``` * ``` pthread_attr_t ``` :thread attribute 描述 thread 的一些特性,目前我們遇到的大部份程式只需要指定為``` pthread_attr_default ```就好。 * ```pthread_create( &a_thread, a_thread_attribute, (void)&thread_function, (void *) &some_argument);```:產生一個thread並執行傳進去的function。 ### 同步問題 * Race Condition:當有2個以上的thread共享同樣的資料,並且他們同時都嘗試去改變它,那最後的結果會因為不同的thread先被執行而有不同。 #### mutex mutex就像一把鎖,可以保護共享的資源。 * 宣告一個mutex變數``` pthread_mutex_t mutex;``` * 初始化mutex``` pthread_mutex_init(&mutex, pthread_mutexattr_default);``` * 將mutex鎖起來,直到解鎖前其他thread不能存取被保護的共享資源``` pthread_mutex_lock( &mutex ); ``` * 將mutex解鎖``` pthread_mutex_unlock( &mutex ); ``` * 當我們不再需要mutex之後可以使用``` pthread_mutex_destroy(&mutex); ```來釋放mutex ## phonebook-concurrent ### 執行看看 THREAD_NUM 4 * cache miss ``` Performance counter stats for './phonebook_opt' (100 runs): 31,0883 cache-misses # 22.999 % of all cache refs ( +- 0.61% ) 135,1713 cache-references ( +- 1.27% ) 2,2886,1173 instructions # 1.10 insns per cycle ( +- 0.04% ) 2,0871,7787 cycles ( +- 0.72% ) 0.149621109 seconds time elapsed ( +- 2.18% ) ``` ![](https://i.imgur.com/MidMRuo.png) ### 理解code #### mmap 將<s>文件</s>檔案的內容映射到一段虛擬記憶體上,通過對這段記憶體的讀取和修改,實現對文件的讀取和修改。 >> 請尊重傳統文化,書寫台灣慣用科技術語。file = 檔案 [name=jserv] >> 好的>< [name=shelly4132] ```c void *mmap(void *start,size_t length, int prot, int flags, int fd, off_t offsize); ``` * start 指向欲映射的核心起始位址,通常設為NULL,代表讓系統自動選定位址,核心會自己在行程位址空間中選擇合適的位址建立映射,映射成功後會返回該位址。 * length 代表映射的大小。將的大小映射到記憶體。 * prot 映射區域的保護方式。 * PROT_EXEC 映射區域可被執行 * PROT_READ 映射區域可被讀取 * PROT_WRITE 映射區域可被寫入 * PROT_NONE 映射區域不能存取 * flags 影響映射區域的各種特性。 * MAP_SHARED 允許其他映射該檔案的行程共享,對映射區域的寫入數據會複製回文件。 * MAP_PRIVATE 不允許其他映射該檔案的行程共享,對映射區域的寫入操作會產生一個映射的複製(copy-on-write),對此區域所做的修改不會寫回原檔案。 * fd 由open返回的檔案描述符,代表要映射到核心中的檔案。 * offsize 從檔案映射開始處的偏移量,通常為0,代表從檔案最前方開始映射。 ### Code Refactoring * 將_append_a裡面的nthread刪掉,有需要用到thread數目的統一用THREAD_NUM代替,還可以減小entry size。 * 將append()裡面原本很多參數的for迴圈改成while讓程式比較好看。 * 利用彥寬學長寫的show_entry()去將字串印出來時發現有缺失,因為在將所有entry串成一條的時候,他一開始就從pNext開始所以導致前面4個字串被漏掉了,改成從pHead開始就ok了。 ### 改進方向 * Thread pool 建立thread需要系統資源,如果我們每次需要的時候才建立thread,不要的時候就丟掉,當數量多時其實是會降低效能的。所以thread pool的概念就是建立一個thread的池子,當需要thread的時候就從裡面拿,不用的時候再放回去,有效的重複利用資源。 * [threadpool-mbrossard](https://github.com/mbrossard/threadpool) * 建立一個task,讓thread知道要做什麼事。這裡我們紀錄要執行的 function pointer 與要傳遞的參數。 ```clike= typedef struct { void (*function)(void *); void *argument; } threadpool_task_t; ``` * 使用 pthread_t的pointer來紀錄所有thread(array),head和tail用來紀錄array的offset ```clike= struct threadpool_t { pthread_mutex_t lock; pthread_cond_t notify; pthread_t *threads; threadpool_task_t *queue; int thread_count; int queue_size; int head; int tail; int count; int shutdown; int started; }; ``` ![](https://i.imgur.com/J58TqwL.png) ## 參考 * [Toward Concurrency](https://hackmd.io/s/H10MXXoT) * [Concurrency系列(二): 從Sequenced-Before開始說起](http://enginechang.logdown.com/posts/788206-concurrency-series-2-starting-from-sequenced-before) * [Concurrency系列(三): 朝Happens-Before邁進](http://enginechang.logdown.com/posts/797113-concurrency-series-3-happens-before) * [淺談coroutine與gevent](http://blog.ez2learn.com/2010/07/17/talk-about-coroutine-and-gevent/) * [Getting Started With POSIX Threads (繁體中文翻譯)](http://www.csie.ntu.edu.tw/~r92094/c++/pthread.txt) * [彥寬學長的筆記](https://hackmd.io/s/BkN1JNQp)與[影片](https://www.youtube.com/watch?v=sWtWslsr4Ac) * [記憶體映射函數 mmap 的使用方法](http://welkinchen.pixnet.net/blog/post/41312211-%E8%A8%98%E6%86%B6%E9%AB%94%E6%98%A0%E5%B0%84%E5%87%BD%E6%95%B8-mmap-%E7%9A%84%E4%BD%BF%E7%94%A8%E6%96%B9%E6%B3%95) * [threadpool-mbrossard](https://github.com/mbrossard/threadpool) * [TempoJiJi](https://hackmd.io/s/rymKa4aT)

    Import from clipboard

    Paste your markdown or webpage here...

    Advanced permission required

    Your current role can only read. Ask the system administrator to acquire write and comment permission.

    This team is disabled

    Sorry, this team is disabled. You can't edit this note.

    This note is locked

    Sorry, only owner can edit this note.

    Reach the limit

    Sorry, you've reached the max length this note can be.
    Please reduce the content or divide it to more notes, thank you!

    Import from Gist

    Import from Snippet

    or

    Export to Snippet

    Are you sure?

    Do you really want to delete this note?
    All users will lose their connection.

    Create a note from template

    Create a note from template

    Oops...
    This template has been removed or transferred.
    Upgrade
    All
    • All
    • Team
    No template.

    Create a template

    Upgrade

    Delete template

    Do you really want to delete this template?
    Turn this template into a regular note and keep its content, versions, and comments.

    This page need refresh

    You have an incompatible client version.
    Refresh to update.
    New version available!
    See releases notes here
    Refresh to enjoy new features.
    Your user state has changed.
    Refresh to load new user state.

    Sign in

    Forgot password

    or

    By clicking below, you agree to our terms of service.

    Sign in via Facebook Sign in via Twitter Sign in via GitHub Sign in via Dropbox Sign in with Wallet
    Wallet ( )
    Connect another wallet

    New to HackMD? Sign up

    Help

    • English
    • 中文
    • Français
    • Deutsch
    • 日本語
    • Español
    • Català
    • Ελληνικά
    • Português
    • italiano
    • Türkçe
    • Русский
    • Nederlands
    • hrvatski jezik
    • język polski
    • Українська
    • हिन्दी
    • svenska
    • Esperanto
    • dansk

    Documents

    Help & Tutorial

    How to use Book mode

    Slide Example

    API Docs

    Edit in VSCode

    Install browser extension

    Contacts

    Feedback

    Discord

    Send us email

    Resources

    Releases

    Pricing

    Blog

    Policy

    Terms

    Privacy

    Cheatsheet

    Syntax Example Reference
    # Header Header 基本排版
    - Unordered List
    • Unordered List
    1. Ordered List
    1. Ordered List
    - [ ] Todo List
    • Todo List
    > Blockquote
    Blockquote
    **Bold font** Bold font
    *Italics font* Italics font
    ~~Strikethrough~~ Strikethrough
    19^th^ 19th
    H~2~O H2O
    ++Inserted text++ Inserted text
    ==Marked text== Marked text
    [link text](https:// "title") Link
    ![image alt](https:// "title") Image
    `Code` Code 在筆記中貼入程式碼
    ```javascript
    var i = 0;
    ```
    var i = 0;
    :smile: :smile: Emoji list
    {%youtube youtube_id %} Externals
    $L^aT_eX$ LaTeX
    :::info
    This is a alert area.
    :::

    This is a alert area.

    Versions and GitHub Sync
    Get Full History Access

    • Edit version name
    • Delete

    revision author avatar     named on  

    More Less

    Note content is identical to the latest version.
    Compare
      Choose a version
      No search result
      Version not found
    Sign in to link this note to GitHub
    Learn more
    This note is not linked with GitHub
     

    Feedback

    Submission failed, please try again

    Thanks for your support.

    On a scale of 0-10, how likely is it that you would recommend HackMD to your friends, family or business associates?

    Please give us some advice and help us improve HackMD.

     

    Thanks for your feedback

    Remove version name

    Do you want to remove this version name and description?

    Transfer ownership

    Transfer to
      Warning: is a public team. If you transfer note to this team, everyone on the web can find and read this note.

        Link with GitHub

        Please authorize HackMD on GitHub
        • Please sign in to GitHub and install the HackMD app on your GitHub repo.
        • HackMD links with GitHub through a GitHub App. You can choose which repo to install our App.
        Learn more  Sign in to GitHub

        Push the note to GitHub Push to GitHub Pull a file from GitHub

          Authorize again
         

        Choose which file to push to

        Select repo
        Refresh Authorize more repos
        Select branch
        Select file
        Select branch
        Choose version(s) to push
        • Save a new version and push
        • Choose from existing versions
        Include title and tags
        Available push count

        Pull from GitHub

         
        File from GitHub
        File from HackMD

        GitHub Link Settings

        File linked

        Linked by
        File path
        Last synced branch
        Available push count

        Danger Zone

        Unlink
        You will no longer receive notification when GitHub file changes after unlink.

        Syncing

        Push failed

        Push successfully