主頁 >  其他 > Linux系統編程之行程控制

Linux系統編程之行程控制

2021-08-18 08:02:22 其他

文章目錄

  • 1.行程創建
    • 1.1 fork函式的回傳值
    • 1.2 寫時拷貝
    • 1.3 fork函式的用法及其呼叫失敗的原因
  • 2.行程終止
    • 2.1 行程終止的原因
    • 2.2 常見的行程退出方法
  • 3.行程等待
    • 3.1 為什么要有行程等待?
    • 3.2 行程等待的方法
      • 3.2.1 wait函式
      • 3.2.2 waitpid函式
      • 3.3.3 子行程的status
  • 4.行程替換
    • 4.1行程替換的原理
    • 4.2 環境變數
      • 4.2.1常見的環境變數
      • 4.2.2與環境變數相關的函式
      • 4.2.3 環境變數的組織形式
    • 4.3 exec函式族
      • 4.3.1 exec函式族的使用
      • 4.3.2 行程替換的應用

1.行程創建

在上一節講解行程概念時,我們提到fork函式是從已經存在的行程中創建一個新行程,那么,系統是如何創建一個新行程的呢?這就需要我們更深入的剖析fork函式,

1.1 fork函式的回傳值

呼叫fork創建行程時,原行程為父行程,新行程為子行程,運行man fork后,我們可以看到如下資訊:

#include <unistd.h>
pid_t fork(void);

fork函式有兩個回傳值,子行程中回傳0,父行程回傳子行程pid,如果創建失敗則回傳-1,

實際上,當我們呼叫fork后,系統內核將會做:

  • 分配新的記憶體塊和內核資料結構(如task_struct)給子行程
  • 將父行程的部分資料結構內容拷貝至子行程
  • 添加子行程到系統行程串列中
  • fork回傳,開始調度
    在這里插入圖片描述

1.2 寫時拷貝

在創建行程的程序中,默認情況下,父子行程共享代碼,但是資料是各自私有一份的,如果父子只需要對資料進行讀取,那么大多數的資料是不需要私有的,這里有三點需要注意:

第一,為什么子行程也會從fork之后開始執行?

因為父子行程是共享代碼的,在給子行程創建PCB時,子行程PCB中的大多數資料是父行程的拷貝,這里面就包括了程式計數器(PC),由于PC中的資料是即將執行的下一條指令的地址,所以當fork回傳之后,子行程會和父行程一樣,都執行fork之后的代碼,

第二,創建行程時,子行程需要拷貝父行程所有的資料嗎?

父行程的資料有很多,但并不是所有的資料都要立馬使用,因此并不是所有的資料都進行拷貝,一般情況下,只有當父行程或者子行程對某些資料進行寫操作時,作業系統才會從記憶體中申請記憶體塊,將新的資料拷寫入申請的記憶體塊中,并且更改頁表對應的頁表項,這就是寫時拷貝,原理如下圖所示:
在這里插入圖片描述

第三,為什么資料要各自私有?

這是因為行程具有獨立性,每個行程的運行不能干擾彼此,

1.3 fork函式的用法及其呼叫失敗的原因

fork函式的用法:

  • 一個父行程希望復制自己,通過條件判斷,使父子行程分流同時執行不同的代碼段,例如,父行程等待客戶端請求,生成子 行程來處理請求,
  • 如子行程從fork回傳后,呼叫行程替換的函式,如exec等(將會在本節4.程式替換中講解),

fork函式呼叫失敗的原因:

  • 系統中行程太多
  • 實際用戶的行程數超過了限制

2.行程終止

2.1 行程終止的原因

行程終止的原因有三種

  • 代碼運行完畢,結果正確
  • 代碼運行完畢,結果不正確
  • 代碼例外終止

2.2 常見的行程退出方法

行程正常終止

1.從main函式return,這是最常見的行程退出方法,在函式設計中,0代表正確,非0代表錯誤,其中不同的非0的退出碼對應了退出原因,

2.呼叫exit或者_exit

_exit函式是系統呼叫,執行man _exit可以看到

#include <unistd.h>
void _exit(int status);

status 定義了行程的終止狀態,父行程可以通過wait來獲得子行程的status(會在3.行程等待中講解),

需要注意的是,exit函式是庫函式,雖然status是int,但是僅有低8位可以被父行程所用,所以_exit(-1)時,在終端執行echo $?發現回傳值是255,

#include <stdlib.h>
void exit(int status);

從作用上來看,_exit和exit是相似的,exit是對_exit的封裝,exit的執行實際上是通過呼叫_exit來實作的,

但是二者也有一些細微的差別,請看如下代碼段:

代碼1

int main()
{
 printf("Hello world");
 exit(0);
}

在這里插入圖片描述

代碼2

 #include<stdio.h>  
 #include<unistd.h>  
 int main()  
 {  
   printf("Hello world");  
    _exit(0);  

在這里插入圖片描述

相比于_exit函式,exit函式先要執行用戶定義的清理函式,在沖刷緩沖區,關閉所有打開的流,將所有的快取資料寫入檔案后,再呼叫_exit,因此我們可以看到,執行exit輸出了“hello World",而執行_exit并沒有輸出,

那么,return和exit有什么區別呢?

在普通函式中,return是用來終止函式的,只有在main函式中才是終止行程,而exit無論在哪里,一旦呼叫,整個行程就會終止,

3.行程等待

3.1 為什么要有行程等待?

在講行程概念時我們提到,當子行程退出,父行程如果不管不顧,子行程殘留資源(PCB)存放于內核中,就可能會造成僵尸行程,如果該資源不能得到釋放,就會導致記憶體泄漏,僵尸行程是不能使用 kill -9 命令清除掉的,因為 kill 命令只是用來終止行程的, 而僵尸行程已經終止,

同時,父行程派給子行程的任務完成的如何,我們是需要知道的,例如,子行程運行完成,結果對還是不對, 或者是否正常退出,

因此,就需要父行程通過行程等待的方式,回收子行程的資源,

3.2 行程等待的方法

一個行程在終止時會關閉所有檔案,釋放在用戶空間分配的記憶體,但它的 PCB 還保留著,內核在其中保存了一些資訊:如果是正常終止則保存著退出狀態,如果是例外終止則保存著導致該行程終止的信號是哪個,當這個行程的父行程呼叫 wait 或 waitpid 獲取這些資訊后,才會將這個行程徹底清除掉,

一個行程的退出狀態可以在 Shell 中通過運行echo $?查看,因為 Shell 是它的父行程,當它終止時 Shell 呼叫 wait 或 waitpid 得到它的退出 狀態同時徹底清除掉這個行程,

3.2.1 wait函式

#include<sys/types.h>
#include<sys/wait.h>
pid_t wait(int*status);
  • 回傳值:成功回傳被等待行程pid,失敗回傳-1,
  • status:是一個輸出型引數,將wait函式內部計算的結果通過status回傳給呼叫者,父行程從而獲取子行程退出狀態,如果不關心子行程的退出狀態則可以將引數設定成為NULL,

這里提一下輸入型引數和輸出型引數的區別,輸入型引數是呼叫者給函式傳的引數,而輸出型引數是是函式將內部計算結果回傳給呼叫者,因此輸出型引數往往用指標,

父行程呼叫 wait 函式可以回收子行程終止資訊,該函式有三個功能:

  • 阻塞等待子行程退出
  • 回收子行程殘留資源
  • 獲取子行程結束狀態(退出原因),

當父行程呼叫wait得到傳出引數status后,可以借助宏函式來進一步判斷行程終止的具體原因:

WIFEXITED(status): 若為正常終止子行程回傳的狀態,則為真,(查看行程是否是正常退出

WEXITSTATUS(status): 若WIFEXITED非零,說明子行程正常終止,提取子行程退出碼,(查看行程的退出碼(exit 的引數))

3.2.2 waitpid函式

作用同 wait,但waitpid可指定 pid 行程清理,可以通過非阻塞方式等待子行程退出,

pid_ t waitpid(pid_t pid, int *status, int options);

pid:

  • pid = -1,等待任一子行程退出,此時與wait等效
  • pid > 0, 回收指定 ID 的子行程,pid為指定行程的行程號,如果不存在該子行程,則立即出錯回傳

status:

  • 同wait

option:

  • 0:阻塞模式,即父行程會阻塞在waitpid處,等到子行程退出后繼續,
  • WNOHANG: 非阻塞模式,若pid指定的子行程沒有結束,則waitpid函式回傳0,不予以等待,若正常結束,則回傳該子行程的ID,一般情況下,非阻塞模式需要搭配回圈使用,

注意:一次 wait 或 waitpid 呼叫只能清理一個子行程,清理多個子行程應使用回圈,

回傳值:

  • 當正常回傳的時候waitpid回傳收集到的子行程的行程ID;
  • 如果設定了選項WNOHANG,而呼叫中waitpid發現沒有已退出的子行程可收集,則回傳0;
  • 如果呼叫中出錯,則回傳-1,這時errno會被設定成相應的值以指示錯誤所在

3.3.3 子行程的status

關于status的用法,我已經在wait函式處講解,此處不再贅述,這里將從底層的角度剖析status的含義,

status不能簡單的當作整形來看待,可以當作位圖來看待,具體細節如下圖(只研究status低16位元位),

在這里插入圖片描述

我們以下一段代碼為例,來展示一下非阻塞等待方式

#include <stdio.h> 
#include <unistd.h>
#include <stdlib.h>
#include <sys/wait.h>
int main()
{
   pid_t pid;
    
    pid = fork();
    if(pid < 0){
       printf("%s fork error\n",__FUNCTION__);
        return 1;
         
    }else if( pid == 0  ){ //child
     printf("child is run, pid is : %d\n",getpid());
     sleep(5);
     exit(1);
    } else{
       int status = 0;
       pid_t ret = 0;
       do
       {
       ret = waitpid(-1, &status, WNOHANG);//非阻塞式等待
       if( ret == 0  ){
       printf("child is running\n");
       }
       sleep(1); 
       }while(ret == 0);
          
       if( WIFEXITED(status) && ret == pid  ){
          printf("wait child 5s success, child return codeis:%d.\n",WEXITSTATUS(status)); 
          }else{
          printf("wait child failed, return.\n");
          return 1;
          }
    }
     return 0;
}

這段代碼先創建子行程,讓子行程等待5s再退出,父行程每1s檢查一下,5s后子行程退出,ret將變成子行程的行程號,退出回圈等待,最終的運行結果如下:

在這里插入圖片描述

4.行程替換

4.1行程替換的原理

在講行程替換原理前,我們需要先知道什么是行程替換,在講fork函式時我們提到,fork 創建子行程后執行的是和父行程相同的程式(但有可能執行不同的代碼分支),如果此時我們用一個新的程式替換掉子行程的地址空間、代碼段和資料,子行程將會從新程式的啟動例程開始執行,這就是行程替換,

行程替換并不是創建新的行程,因為替換前后該行程的PID并未改變,

4.2 環境變數

行程替換需要用到一種exec函式,在講exec函式族之前,我們先介紹一下環境變數的概念,

4.2.1常見的環境變數

按照慣例,環境變數字串都是name=value 這樣的形式,大多數 name 由大寫字母加下劃線組成,一般把name 的部分叫做環境變數,value 的部分則是環境變數的值,

環境變數定義了行程的運行環境,具有全域屬性,因此設定環境變數時要加export,一些比較重要的環境變數的含義如下:

PATH

可執行檔案的搜索路徑,ls 命令也是一個程式,執行它不需要提供完整的路徑名/bin/ls, 然而通常我們執行當前目錄下的程式 a.out 卻需要提供完整的路徑名./a.out,這是因為 PATH 環境變數的值里面包含了 ls 命令所在的目錄/bin,卻不包含 a.out 所在的目錄,

PATH 環境變數的值可以包含多個目錄,用:號隔開,在 Shell 中用 echo 命令可以查看這個環境變數的值: echo $PATH

在這里插入圖片描述

SHELL

當前 Shell,它的值通常是/bin/bash,

在這里插入圖片描述

TERM

當前終端型別

在這里插入圖片描述

HOME

當前用戶主目錄的路徑,很多程式需要在主目錄下保存組態檔,使得每個用戶在運行該程式時都有自己的一套配置,

在這里插入圖片描述

4.2.2與環境變數相關的函式

getenv函式

獲取環境變數值: char *getenv(const char *name);

成功:回傳環境變數的值;失敗:NULL (name 不存在)

setenv 函式

設定環境變數的值 :int setenv(const char *name, const char *value, int overwrite);

成功:回傳0;失敗: 回傳-1

引數 overwrite 取值:

1:覆寫原環境變數

0:不覆寫,(該引數常用于設定新環境變數,如:HELLO = “hello”)

unsetenv 函式

洗掉環境變數 name 的定義: int unsetenv(const char *name);

成功:0;失敗:-1

注意事項:name 不存在仍回傳 0(成功),

4.2.3 環境變數的組織形式

在這里插入圖片描述

environ 變數是一個char ** 型別,存盤著系統的環境變數,每個程式都會收到一張環境表,環境表是一個字符指標陣列,每個指標指向一個以’\0’結尾的環境字串,

4.3 exec函式族

4.3.1 exec函式族的使用

知道了環境變數的概念后,再簡要介紹一下命令列引數,當我們在某個目錄下輸入ls -als -l時,會有如下顯示:

在這里插入圖片描述

我們發現,同樣的ls命令,由于后面所跟的字串不同,顯示了不同的結果,這里的“-a”,“-l”被稱為引數,實際上,一個程式內可以通過加入引數,讓相同的程式執行不同的功能,

接下來我們來介紹行程替換必不可少的函式族——exec函式族,

其實有六種以 exec 開頭的函式,統稱 exec 函式:

int execl(const char *path, const char *arg, ...); 

int execlp(const char *file, const char *arg, ...);

int execle(const char *path, const char *arg, ..., char *const envp[]);

int execv(const char *path, char *const argv[]);

int execvp(const char *file, char *const argv[]); 

int execve(const char *path, char *const argv[], char *const envp[]);

注意:這些函式如果呼叫成功則加載新的程式從啟動代碼開始執行,不再回傳, 如果呼叫出錯則回傳-1 所以exec函式只有出錯的回傳值而沒有成功的回傳值

這些函式如何使用,我們來看下面這段代碼:

#include <unistd.h>
int main()
{
 char *const argv[] = {"ps", "-ef", NULL};//argv[0]始終是程式名
 char *const envp[] = {"PATH=/bin:/usr/bin", "TERM=console", NULL};
 //execl("/bin/ps", "ps", "-ef", NULL);
 
 // 帶p的,可以使用環境變數PATH,無需寫全路徑
 //execlp("ps", "ps", "-ef", NULL);
 
 
 // 帶e的,需要自己組裝環境變數
 //execle("ps", "ps", "-ef", NULL, envp);
 
 //execv("/bin/ps", argv);
 
 // 帶p的,可以使用環境變數PATH,無需寫全路徑
 //execvp("ps", argv);

 // 帶e的,需要自己組裝環境變數
 execve("/bin/ps", argv, envp);
 exit(0);
}

事實上,只有execve是真正的系統呼叫,其它五個函式最終都呼叫 execve,

這些函式原型看起來很容易混,但只要掌握了規律就很好記,

  • l(list) : 表示引數采用串列,如果采用串列形式,const char *arg中的第一個引數必須是可執行程式本身,如上例中的 “ps”,
  • v(vector) : 引數用陣列 ,v和l只能二選一
  • e(env) : 表示自己維護環境變數,有e引數中就需要有char *const envp[]
  • p(path) : 有p自動搜索環境變數PATH,第一個引數直接輸入程式名即可,且有p一定沒有e,因為有表示已經自動添加了環境變數,如果沒有p則需要輸入對應程式的路徑

4.3.2 行程替換的應用

我們平時使用的shell讀取命令和分析命令就是一個很典型的例子,如下圖所示:

在這里插入圖片描述

我們平時輸入的如ls -a等命令實際上是一個個可執行程式,當shell讀取一行命令時,shell會對命令進行決議,并且shell創建一個子行程,再通過呼叫execve,用可執行程式替換掉子行程,當程式執行完畢并且退出后,shell讀取子行程的退出資訊,這樣,即便會出現程式崩潰的情況,也不會影響到shell本身,

以上就是關于行程控制的內容,主要分為四個方面——行程創建,行程終止,行程等待以及行程替換,有了以上的知識,我們已經可以實作一個很簡易的shell,如何實作,請讀者自行思考!

轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/294472.html

標籤:其他

上一篇:【資料結構】一篇文章學懂并查集+LRU Cache,拿來吧你!

下一篇:Day6:資料結構之二叉樹

標籤雲
其他(157675) Python(38076) JavaScript(25376) Java(17977) C(15215) 區塊鏈(8255) C#(7972) AI(7469) 爪哇(7425) MySQL(7132) html(6777) 基礎類(6313) sql(6102) 熊猫(6058) PHP(5869) 数组(5741) R(5409) Linux(5327) 反应(5209) 腳本語言(PerlPython)(5129) 非技術區(4971) Android(4554) 数据框(4311) css(4259) 节点.js(4032) C語言(3288) json(3245) 列表(3129) 扑(3119) C++語言(3117) 安卓(2998) 打字稿(2995) VBA(2789) Java相關(2746) 疑難問題(2699) 细绳(2522) 單片機工控(2479) iOS(2429) ASP.NET(2402) MongoDB(2323) 麻木的(2285) 正则表达式(2254) 字典(2211) 循环(2198) 迅速(2185) 擅长(2169) 镖(2155) 功能(1967) .NET技术(1958) Web開發(1951) python-3.x(1918) HtmlCss(1915) 弹簧靴(1913) C++(1909) xml(1889) PostgreSQL(1872) .NETCore(1853) 谷歌表格(1846) Unity3D(1843) for循环(1842)

熱門瀏覽
  • 網閘典型架構簡述

    網閘架構一般分為兩種:三主機的三系統架構網閘和雙主機的2+1架構網閘。 三主機架構分別為內端機、外端機和仲裁機。三機無論從軟體和硬體上均各自獨立。首先從硬體上來看,三機都用各自獨立的主板、記憶體及存盤設備。從軟體上來看,三機有各自獨立的作業系統。這樣能達到完全的三機獨立。對于“2+1”系統,“2”分為 ......

    uj5u.com 2020-09-10 02:00:44 more
  • 如何從xshell上傳檔案到centos linux虛擬機里

    如何從xshell上傳檔案到centos linux虛擬機里及:虛擬機CentOs下執行 yum -y install lrzsz命令,出現錯誤:鏡像無法找到軟體包 前言 一、安裝lrzsz步驟 二、上傳檔案 三、遇到的問題及解決方案 總結 前言 提示:其實很簡單,往虛擬機上安裝一個上傳檔案的工具 ......

    uj5u.com 2020-09-10 02:00:47 more
  • 一、SQLMAP入門

    一、SQLMAP入門 1、判斷是否存在注入 sqlmap.py -u 網址/id=1 id=1不可缺少。當注入點后面的引數大于兩個時。需要加雙引號, sqlmap.py -u "網址/id=1&uid=1" 2、判斷文本中的請求是否存在注入 從文本中加載http請求,SQLMAP可以從一個文本檔案中 ......

    uj5u.com 2020-09-10 02:00:50 more
  • Metasploit 簡單使用教程

    metasploit 簡單使用教程 浩先生, 2020-08-28 16:18:25 分類專欄: kail 網路安全 linux 文章標簽: linux資訊安全 編輯 著作權 metasploit 使用教程 前言 一、Metasploit是什么? 二、準備作業 三、具體步驟 前言 Msfconsole ......

    uj5u.com 2020-09-10 02:00:53 more
  • 游戲逆向之驅動層與用戶層通訊

    驅動層代碼: #pragma once #include <ntifs.h> #define add_code CTL_CODE(FILE_DEVICE_UNKNOWN,0x800,METHOD_BUFFERED,FILE_ANY_ACCESS) /* 更多游戲逆向視頻www.yxfzedu.com ......

    uj5u.com 2020-09-10 02:00:56 more
  • 北斗電力時鐘(北斗授時服務器)讓網路資料更精準

    北斗電力時鐘(北斗授時服務器)讓網路資料更精準 北斗電力時鐘(北斗授時服務器)讓網路資料更精準 京準電子科技官微——ahjzsz 近幾年,資訊技術的得了快速發展,互聯網在逐漸普及,其在人們生活和生產中都得到了廣泛應用,并且取得了不錯的應用效果。計算機網路資訊在電力系統中的應用,一方面使電力系統的運行 ......

    uj5u.com 2020-09-10 02:01:03 more
  • 【CTF】CTFHub 技能樹 彩蛋 writeup

    ?碎碎念 CTFHub:https://www.ctfhub.com/ 筆者入門CTF時時剛開始刷的是bugku的舊平臺,后來才有了CTFHub。 感覺不論是網頁UI設計,還是題目質量,賽事跟蹤,工具軟體都做得很不錯。 而且因為獨到的金幣制度的確讓人有一種想去刷題賺金幣的感覺。 個人還是非常喜歡這個 ......

    uj5u.com 2020-09-10 02:04:05 more
  • 02windows基礎操作

    我學到了一下幾點 Windows系統目錄結構與滲透的作用 常見Windows的服務詳解 Windows埠詳解 常用的Windows注冊表詳解 hacker DOS命令詳解(net user / type /md /rd/ dir /cd /net use copy、批處理 等) 利用dos命令制作 ......

    uj5u.com 2020-09-10 02:04:18 more
  • 03.Linux基礎操作

    我學到了以下幾點 01Linux系統介紹02系統安裝,密碼啊破解03Linux常用命令04LAMP 01LINUX windows: win03 8 12 16 19 配置不繁瑣 Linux:redhat,centos(紅帽社區版),Ubuntu server,suse unix:金融機構,證券,銀 ......

    uj5u.com 2020-09-10 02:04:30 more
  • 05HTML

    01HTML介紹 02頭部標簽講解03基礎標簽講解04表單標簽講解 HTML前段語言 js1.了解代碼2.根據代碼 懂得挖掘漏洞 (POST注入/XSS漏洞上傳)3.黑帽seo 白帽seo 客戶網站被黑帽植入劫持代碼如何處理4.熟悉html表單 <html><head><title>TDK標題,描述 ......

    uj5u.com 2020-09-10 02:04:36 more
最新发布
  • 2023年最新微信小程式抓包教程

    01 開門見山 隔一個月發一篇文章,不過分。 首先回顧一下《微信系結手機號資料庫被脫庫事件》,我也是第一時間得知了這個訊息,然后跟蹤了整件事情的經過。下面是這起事件的相關截圖以及近日流出的一萬條資料樣本: 個人認為這件事也沒什么,還不如關注一下之前45億快遞資料查詢渠道疑似在近日復活的訊息。 訊息是 ......

    uj5u.com 2023-04-20 08:48:24 more
  • web3 產品介紹:metamask 錢包 使用最多的瀏覽器插件錢包

    Metamask錢包是一種基于區塊鏈技術的數字貨幣錢包,它允許用戶在安全、便捷的環境下管理自己的加密資產。Metamask錢包是以太坊生態系統中最流行的錢包之一,它具有易于使用、安全性高和功能強大等優點。 本文將詳細介紹Metamask錢包的功能和使用方法。 一、 Metamask錢包的功能 數字資 ......

    uj5u.com 2023-04-20 08:47:46 more
  • vulnhub_Earth

    前言 靶機地址->>>vulnhub_Earth 攻擊機ip:192.168.20.121 靶機ip:192.168.20.122 參考文章 https://www.cnblogs.com/Jing-X/archive/2022/04/03/16097695.html https://www.cnb ......

    uj5u.com 2023-04-20 07:46:20 more
  • 從4k到42k,軟體測驗工程師的漲薪史,給我看哭了

    清明節一過,盲猜大家已經無心上班,在數著日子準備過五一,但一想到銀行卡里的余額……瞬間心情就不美麗了。最近,2023年高校畢業生就業調查顯示,本科畢業月平均起薪為5825元。調查一出,便有很多同學表示自己又被平均了。看著這一資料,不免讓人想到前不久中國青年報的一項調查:近六成大學生認為畢業10年內會 ......

    uj5u.com 2023-04-20 07:44:00 more
  • 最新版本 Stable Diffusion 開源 AI 繪畫工具之中文自動提詞篇

    🎈 標簽生成器 由于輸入正向提示詞 prompt 和反向提示詞 negative prompt 都是使用英文,所以對學習母語的我們非常不友好 使用網址:https://tinygeeker.github.io/p/ai-prompt-generator 這個網址是為了讓大家在使用 AI 繪畫的時候 ......

    uj5u.com 2023-04-20 07:43:36 more
  • 漫談前端自動化測驗演進之路及測驗工具分析

    隨著前端技術的不斷發展和應用程式的日益復雜,前端自動化測驗也在不斷演進。隨著 Web 應用程式變得越來越復雜,自動化測驗的需求也越來越高。如今,自動化測驗已經成為 Web 應用程式開發程序中不可或缺的一部分,它們可以幫助開發人員更快地發現和修復錯誤,提高應用程式的性能和可靠性。 ......

    uj5u.com 2023-04-20 07:43:16 more
  • CANN開發實踐:4個DVPP記憶體問題的典型案例解讀

    摘要:由于DVPP媒體資料處理功能對存放輸入、輸出資料的記憶體有更高的要求(例如,記憶體首地址128位元組對齊),因此需呼叫專用的記憶體申請介面,那么本期就分享幾個關于DVPP記憶體問題的典型案例,并給出原因分析及解決方法。 本文分享自華為云社區《FAQ_DVPP記憶體問題案例》,作者:昇騰CANN。 DVPP ......

    uj5u.com 2023-04-20 07:43:03 more
  • msf學習

    msf學習 以kali自帶的msf為例 一、msf核心模塊與功能 msf模塊都放在/usr/share/metasploit-framework/modules目錄下 1、auxiliary 輔助模塊,輔助滲透(埠掃描、登錄密碼爆破、漏洞驗證等) 2、encoders 編碼器模塊,主要包含各種編碼 ......

    uj5u.com 2023-04-20 07:42:59 more
  • Halcon軟體安裝與界面簡介

    1. 下載Halcon17版本到到本地 2. 雙擊安裝包后 3. 步驟如下 1.2 Halcon軟體安裝 界面分為四大塊 1. Halcon的五個助手 1) 影像采集助手:與相機連接,設定相機引數,采集影像 2) 標定助手:九點標定或是其它的標定,生成標定檔案及內參外參,可以將像素單位轉換為長度單位 ......

    uj5u.com 2023-04-20 07:42:17 more
  • 在MacOS下使用Unity3D開發游戲

    第一次發博客,先發一下我的游戲開發環境吧。 去年2月份買了一臺MacBookPro2021 M1pro(以下簡稱mbp),這一年來一直在用mbp開發游戲。我大致分享一下我的開發工具以及使用體驗。 1、Unity 官網鏈接: https://unity.cn/releases 我一般使用的Apple ......

    uj5u.com 2023-04-20 07:40:19 more