网络应用与服务

客户端必须与它们相应的网络服务器连接起来才能正常工作。Unix服务器有很多种形式。服务器程序直接或间接地监听端口。另外,服务器功能各异,但没有通用的配置数据库。大多数服务器通过配置文件(尽管格式不统一)来定义自身的行为,并使用操作系统的syslog服务来记录日志。接下来我们会介绍一些常见的服务器以及用于调试的工具。

服务的基本概念

TCP服务是最好理解的概念之一,因为它建立在简单、无中断的双路数据流之上。或许最佳的解释方式,是让你直接通过TCP与某个Web服务器的80端口沟通,去看看数据是如何在该连接上移动的。例如,用以下命令连接一个Web服务器:

$ telnet www.wikipedia.org 80

你会得到类似这样的输出:

Trying some address...
Connected to www.wikipedia.org.
Escape character is '^]'.

现在输入:

GET / HTTP/1.0

这个测试告诉我们:

  • 远程主机那里有个Web服务器进程监听着TCP端口80;
  • telnet是初始化这个连接的客户端。

输入剖析

$ curl --trace-ascii trace_file http://www.wikipedia.org/

你会得到大量的HTML输出。忽略它们(或将它们重定向到/dev/null),并去看看刚刚创建出来的文件trace_file。假设连接成功,那么文件的开头部分看起来应该是下面这样的,表明刚开始时curl尝试跟该服务器建立TCP连接:

== Info: About to connect() to www.wikipedia.org port 80 (#0)
== Info: Trying 10.80.154.224... == Info: connected

至此你看到的一切都是发生在传输层或其下层的。然而,如果连接成功了,那么curl就会尝试发送请求(即“报头”);这里就开始有应用层了。

=> Send header, 167 bytes (0xa7)
0000: GET / HTTP/1.1
0010: User-Agent: curl/7.22.0 (i686-pc-linux-gnu) libcurl/7.22.0 OpenS
0050: SL/1.0.1 zlib/1.2.3.4 libidn/1.23 librtmp/2.3
007f: Host: www.wikipedia.org
0098: Accept: */*
00a5:

上例第一行是curl的调试信息输出,告诉了你它接下来要做的事情。剩下的行展示了curl发送给服务器的信息。开头的十六进制数只是一个调试偏移量,告诉你收发的数据有多少。

你可以看到curl先发了一个GET命令给服务器(就像用telnet那样),接着是一些有关服务器的额外信息以及一个空行。然后服务器回应了,首先是它的报头(粗体部分)。

<= Recv header, 17 bytes (0x11)
0000: HTTP/1.1 200 OK
<= Recv header, 16 bytes (0x10)
0000: Server: Apache
<= Recv header, 42 bytes (0x2a)
0000: X-Powered-By: PHP/5.3.10-1ubuntu3.9+wmf1
--snip--

跟之前那段输出很像,<=开头的行是调试信息,0000:是偏移量

服务器回应的报头可以很长,然后,某行的报头出现了我们请求的内容,就像下面这样:

<= Recv header, 55 bytes (0x37)
0000: X-Cache: cp1055 hit (16), cp1054 frontend hit (22384)
<= Recv header, 2 bytes (0x2)
0000:
<= Recv data, 877 bytes (0x36d)
0000: 008000
0008: <!DOCTYPE html>.<html lang="mul" dir="ltr">.<head>.<!-- Sysops:
--snip--

尽管调试信息里有Recv header和Recv data,意味着服务器返回的信息可分为两种,但curl向操作系统获取这两种信息的方法却没有不同,操作系统对它们的处理方式也没有不同,甚至底层网络对它们的数据包的处理方式也是一样的。如果说有不同,那完全是在用户空间的curl内部。curl读取报头的时候,如果发现了标志HTTP报头
结束的空行(即中间的两个字节),它就知道接下来将是真正的应答内容了。

在服务器发送数据方面也同样如此。服务器并不区分发给操作系统的报头和内容,区分只发生于用户空间的服务器程序。

网络服务器

大多数网络服务器跟cron之类的服务器守护进程很像,只不过网络服务器是与网络端口进行交互的。

以下是一些常见的网络服务器,在你系统中可能也会见到

  • httpd、apache、apache2:Web服务器。
  • sshd:Secure shell守护进程。
  • postfix、qmail、sendmail:邮件服务器。
  • cupsd:打印服务器。
  • nfsd、mountd:网络文件系统(文件共享)守护进程。
  • smbd、nmbd:文件共享守护进程
  • rpcbind:远程程序调用(RPC)端口映射服务守护进程。

大多数网络服务器有一个共同的特性,即它们通常是多进程的。其中至少有一个进程在监听网络端口,而当它接收到一个新的连接时,就会使用fork()来创建一个子进程,负责那个新的连接。该子进程,也叫辅助进程,会随着连接的终止而终止。同时,监听进程会继续接收连接。这样,一个服务器就能轻松地处理多个连接,一般不会有什么问题。

然而,这个模型也会有一些异常情况。调用fork()是会增加系统负担的,而高性能TCP服务器(如Apache Web服务器)能在启动时就创建一定数量的辅助进程,以备连接需要。接受UDP包的服务器只会简单地接收数据并对其做出反应,它们不需要维持连接。

SSH

SSH是最常见的网络服务应用之一,它是一种远程连接Unix机器的标准。配置好之后,我们就能通SSH进行安全的shell登录、执行远程程序、共享简单的文件等。

SSH还凭借公钥认证和简单的会话加密,取代了旧的、不安全的远程登录系统telnet和rlogin。大多数ISP和云提供商都要求以SSH来使用他们的服务,另外很多基于Linux的网络设备(如NAS)也是这样要求的。OpenSSH(http://www.openssh.com/)是一个比较流行的、针对Unix的SSH实现,而且几乎所有的Linux发行版也预装了它。OpenSSH的客户端是ssh,服务器是sshd。SSH协议有两个主要版本:1和2。OpenSSH对两者都支持,但1是很少用的。

SSH的功能和特性使它能做到以下事情。

  • 对密码和会话内容加密,保护你不受窃听困扰。
  • 作为其他网络连接的管道,包括来自X Window客户端的连接。X会在第14章详细介绍。
  • 几乎所有操作系统都可用SSH连接。
  • 使用密钥做主机认证。

但SSH也有缺点。其中一个就是,若想建立SSH连接,你必须先知道远程主机的公钥,它是不需要通过什么保密的渠道就能获得的(当然你也可以手动检查它的真假)

SSHD服务器

运行sshd需要一个配置文件以及主机密钥。大多数发行版都将配置文件放在/etc/ssh配置目录中,并在你安装它们的sshd包时,尝试将一切都配置好。(这里的配置文件名sshd_config跟客户端的文件名ssh_config很容易混淆,请注意区分。)

Port 22
#Protocol 2,1
#ListenAddress 0.0.0.0
#ListenAddress ::
HostKey /etc/ssh/ssh_host_key
HostKey /etc/ssh/ssh_host_rsa_key
HostKey /etc/ssh/ssh_host_dsa_key

以#开头的是注释,而sshd_config中的很多的注释都暗示了默认值。sshd_config(5)手册包含了所有可选值的解释,而以下这些是最重要的。

  • HostKey file:使用file作为主机密钥。(主机密钥是短的。)
  • LogLevel level:按照syslog的级别level来记录信息。
  • PermitRootLogin value:value为yes则允许超级用户通过SSH登录,否则不允许。
  • SyslogFacility name:按syslog设施的名字name来记录信息。
  • X11Forwarding value:若value为yes则允许X Window客户端被SSH管道接驳。
  • XAuthLocation path:设置xauth的路径。找不到路径的话,X11的SSH管道将无法工作。如果xauth不在/usr/bin里,则需写明xauth的完整路径。

主机密匙

OpenSSH有三套主机密钥:一套用于版本1的协议,另两套用于版本2。每套都有一个公钥(扩展名为.pub的文件)和一个私钥(无扩展名)。不要让任何人知道你的私钥,否则就有被入侵的危险。

SSH版本1只有RSA密钥,而版本2则有RSA和DSA。RSA和DSA都是公钥加密算法。

文件名 密钥类型
ssh host_rsa_key RSA私钥(版本2)
ssh host_rsa_key.pub RSA公钥(版本2)
ssh host_dsa_key DSA私钥(版本2)
ssh host_dsa_key.pub DSA公钥(版本2)
ssh host_key RSA私钥(版本1)
ssh host key.pub RSA公钥(版本1)

SSH服务器与客户端还用到了一个叫作ssh_known_hosts的密钥文件,里面包含了其他主机的公钥。如果你要使用基于主机的认证,服务器端的ssh_known_hosts必须要包含所有可信客户端的公钥。了解密钥文件有助于你更换机器。当你从头给机器安装系统时,你可以用回旧的机器上的密钥文件,这样用户就能跟旧的密钥配置对上了。

开启SSH服务器

尽管大多数发行版都带有SSH,但默认却不会启动sshd服务器。在Ubuntu和Debian上,安装SSH服务器就会创建密钥、启动服务,并在开机脚本中加上启动SSH。在Fedora上,sshd是预装的,但默认是关闭的。想在开机时启动sshd,可以用chkconfig(但这并不会让服务器马上启动,除非你用service sshd start):

# chkconfig sshd on

Fedora一般会在sshd初次启动时补建漏掉的密钥文件。
如果你还没装好init的支持,就用root来运行sshd,以启动服务器。而一旦启动,sshd就会在/var/run/sshd.pid记下自己的PID。

你还可以在systemd或用inetd以套接字单元来启动sshd,但这不是个好方法,因为服务器偶尔会产生密钥文件,这个进程可能会很费时间。

SSH客户端

想登录远程主机,运行:

ssh remote_username@host

如果你在本机的账号跟远程的一样,可以省略remote_username@。你还可以像下面例子一样用管道符来连接ssh命令,将一个叫dir的目录复制到另一台主机:

tar zcvf - dir | ssh remote_host tar zxvf -

全局的SSH客户端配置文件ssh_config应该在/etc/ssh里,就如sshd_config文件一样。跟服务器配置文件类似,客户端配置文件也有键值对,但你应该不用去改它。

SSH文件传输客户端

OpenSSH包含了文件传输程序:scp和sftp。这两个命令用以取代旧的、不安全的命令rcp和ftp。

你可以用scp在本机和远程主机之间传输文件,它就像cp命令一样。以下是一些例子。

$ scp user@host:file .
$ scp file user@host:dir
$ scp user1@host1:file user2@host2:dir

sftp程序就好比是命令行的ftp客户端,它有get和put命令。远程主机必须装好sftp-server程序(如果远端装了OpenSSH,那通常都会带上这个)。

非Unix平台的SSH客户端

PuTTY是一个不错的基本Windows客户端,它包含了安全的文件复制程序。MacSSH适用于Mac OS 9.x及以下版本。Mac OS X是基于Unix的,也包含OpenSSH

守护进程inetd和xinetd

为每种服务实现独立的服务器好像并不太高效。每个服务器都要分别配置端口监听、访问控制以及端口设置。大多数服务的配置方式都是一样的,只是处理连接的方式不同。

传统的解决方法是使用inetd守护进程,它是一种超级服务器,用于规范网络端口的接入和服务器程序与网络端口之间的接口。启动inetd之后,它会读取自己的配置文件,并监听其中提到的网络端口。当连接到来时,inetd就会新开一个进程来处理它。

xinetd是inetd的新版本,它提供更简单的配置和更优秀的访问控制,但xinetd正被systemd取代,systemd的套接字单元能提供同样的功能。

ident stream tcp nowait root /usr/sbin/sshd sshd -i

其中7个字段从左至右含义分别如下所示。

  • 服务名称:来自/etc/services(见9.14.3节)。
  • 套接字类型:通常TCP是stream,UDP是dgram。
  • 协议:传输协议,通常是tcp或udp。
  • 数据报服务器行为:UDP可选wait或nowait。其他传输协议应该用nowait。
  • 用户:运行该服务的用户。加上.group的话,可以指定群组。
  • 可执行程序:inetd为应付该服务而发起的程序。
  • 参数:可执行程序的参数。第一个参数是该程序的名字。

诊断工具

tcpdump

如果你想明确地知道你的网络上有什么在流通,你可用tcpdump将网络接口置于混杂模式,并向你报告每一个通过的数据包。不带参数地运行tcpdump,就包含了ARP请求和Web连接。

你可以加入过滤器,以让tcpdump的内容更精确。过滤器可以是源主机、目标主机、网络、以太网地址、各层协议等等。各种数据包协议中,tcpdump能认出的有:ARP、RARP、ICMP、TCP、UDP、IP、IPv6、AppleTalk、IPX。例如,让tcpdump只输出TCP数据包,可运行:

# tcpdump tcp

想看网页包和UDP包,运行:

# tcpdump udp or port 80

netcat

netcat可以与TCP和UDP端口通信,指定本地端口,监听端口,扫描端口,对网络输入输出重定向到标准输入输出等等。

用netcat连接TCP端口

$ netcat host port

netcat只在对方关闭连接时终止,所以如果你用netcat接收标准输入,就会有点麻烦。你可以使用CTRL-C来随时关闭连接。(如果你希望由标准输入流来决定程序和网络连接的关闭,可以改用sock程序。)

扫描端口

有时你可能想知道你网络中的机器正提供着什么服务,或哪个IP正在被使用,这时你可以用网络映射器(Network Mapper,以下简称Nmap)程序来扫描并列举出一台机器(或一个网络中的机器)的开放端口。

在列举你机器的端口时,至少从这样两个不同的角度来运行Nmap程序会更好:从本机和从另一台机器(可能是本地网络之外的)。这样做可以看到你防火墙屏蔽了什么。

运行nmap host来对一个主机进行端口扫描,例如:

$ nmap 10.1.2.2
Starting Nmap 5.21 ( http://nmap.org ) at 2015-09-21 16:51 PST
Nmap scan report for 10.1.2.2
Host is up (0.00027s latency).
Not shown: 993 closed ports
PORT STATE SERVICE
22/tcp open ssh
25/tcp open smtp
80/tcp open http
111/tcp open rpcbind
8800/tcp open unknown
9000/tcp open cslistener
9090/tcp open zeus-admin
Nmap done: 1 IP address (1 host up) scanned in 0.12 seconds

远程程度调用

RPC意指远程程序调用(Remote Procedure Call),是应用层中较低层的一个系统。它是为了方便程序员访问网络应用而设计的,能使本地程序调用远程程序(按程序号来标识),让远程程序返回结果码或信息。

RPC的实现需要用到传输层协议,如TCP和UDP。它需要一种特别的中介服务来将程序号与TCP和UDP的端口号对应起来。这种服务就是rpcbind,运行RPC服务就需要用到它。

$ rpcinfo -p localhost

RPC是一种难以消亡的协议。网络文件系统(Network File System,以下简称NFS)和网络信息服务(Network Information Service,以下简称NIS)就用得到它,但单机环境下是不需要这些服务的。当你以为你已经对rpcbind不会再有任何需要时,就会有些依赖它的东西出现,例如GNOME的文件访问监控(File Access Monitor,以下简称FAM)。

网络安全

因为Linux是PC平台上风行的Unix系统,尤其是它被广泛用作网页服务器,所以它也招致了很多黑客攻击

网络安全带来了两个极端:真心想攻破系统的人(不管是为了钱还是为了好玩)和精心设计防御方案的人(这个也很有利可图)。幸好,你不需要了解太多东西来维持系统的安全。这里有一些经验法则。

  • 打开的服务越少越好:黑客不能攻击你机器上不存在的服务。如果你知道有哪个服务是你不需要的,那就别打开它,等你真正用到那个服务时再打开。
  • 防火墙屏蔽得越多越好:Unix系统有一些内部服务是你可能不知道的(例如用于RPC端映射的TCP端口111),因此也别让其他机器知道它们的存在。跟踪和规范本机的服务是很困难的,因为监听的程序和被监听的端口错综复杂。为避免黑客发现你系统上的内部服务,请使用有效的防火墙规则,并为路由器安装防火墙。
  • 记录你提供给互联网的服务:如果你运行着SSH服务器、Postfix或类似的东西,请保持你软件的更新,以及使用合适的安全警报
  • 让服务器使用“长期支持”的系统版本:安全团队一般在稳定、有支持的系统版本上才能集中精力工作。开发版或测试版如Debian Unstable和Fedora Rawhide不太受他们关注。
  • 账号不要发给不用的人:通过本地账号获取超级用户的权限,比远程入侵要简单得多。事实上,大多数系统上的软件都有这样那样的漏洞,只要你能登录shell,就有可能获取超级用户的权力。不要指望你的朋友懂得如何保护密码(或懂得使用复杂的密码)。
  • 避免安装可疑的二进制包:它们可能包含木马

有以下三种基本的网络攻击。

  • 全面威胁:意思是获取了超级用户的权限(对一台机器完全掌控)。黑客可以通过服务攻击,例如缓存溢出、接管一个没什么保护措施的账号或利用一个写得不太好的setuid,来做到“全面威胁”。
  • 拒绝服务(Denial-of-service,简称DoS)攻击:这使得机器无法继续提供服务,或无需通过登录就用某些方法造成机器故障。这种攻击更难防范,但很容易应对。
  • 恶意软件:Linux用户大多对恶意软件(如电子邮件蠕虫和病毒)免疫,只因为他们的电子邮件客户端不会蠢到运行附件里的程序。但Linux恶意程序确实存在。请勿从陌生的地方下载并安装二进制软件。

典型漏洞

直接攻击和嗅探明文密码

直接攻击:就是摆明要攻陷一台机器。最常见的做法是利用缓存溢出。该漏洞是因为粗心的程序员没检查数组边界而造成的。攻击者在一大堆数据中编造一个栈帧,然后送到远程服务器,并期望它溢出而覆盖了程序,最终导致服务器执行了栈帧中的东西。尽管这不太容易,但却很容易复制。

嗅探明文密码:是指获取网络上明文传输的密码。一旦攻击者拿到你的密码,那你就玩完了。从那开始,攻击者就会直接登入,尝试获取超级用户的权限(这比远程攻击要简单),或以该机器攻击其他机器,或用其他机器攻击该机器

有些服务因为设计缺陷而经常成为攻击目标。例如以下这些服务:

  • ftpd:不管什么原因,所有的FTP服务器都存在漏洞。除此之外,大多数FTP服务器都用明文密码。如果你要在机器之间移动文件,考虑下基于SSH的方案或rsync服务器。
  • telnetd、rlogind、rexecd:它们都把会话内容(包括密码)用明文传输。不要使用它们,除非你有Kerberos版本。
  • fingerd:黑客可以通过finger服务获取用户列表和其他信息。

安全资源

安全网站:

  • http://www.sans.org/:提供培训、服务、免费的高危漏洞周报、安全策略样板等等。
  • http://www.cert.org/:这里介绍最危险的漏洞。
  • http://www.insecure.org/:这里有Nmap和各种网络开发测试工具,比其他网站做得更详尽、更开放。

套接字:进程与网络的通信方式

在Unix上,进程是用套接字来标识与网络通信的时机与方式的。套接字是进程通过内核访问网络的接口,它代表用户空间与内核空间的边界。它也常被用于进程间通信(Interprocess Communication,以下简称IPC)。

因为进程需要以不同的方式访问网络,所以套接字也分不同种类。例如,TCP连接会用流式套接字(程序员称之为SOCK_STREAM),而UDP连接则用数据报套接字(SOCK_DGRAM)。

建立网络套接字有点复杂,因为你有时需要知道套接字类型、IP地址、端口、传输协议。然而,当所有初始的细节整理好后,服务器就能用相应的标准模型来处理网络通信了。

监听套接字和读写套接字。主进程用监听套接字在网络中寻找连接。当一个新的连接到来,主进程就用accept()系统调用来接收该连接,它能为连接创建专用的读写套接字。接着主进程用fork()创建一个新的子进程来处理该连接。最终,监听套接字继续监听,为主进程带来更多连接。

Unix域套接字

进程间的通信可以使用本地主机(127.0.0.1)来做常规的网络通信,但我们一般使用另一种特别的套接字,进程与Unix域套接字的连接几乎与网络套接字连接一样:进程可以监听和接收套接字上的连接,还可以选择不同类型的套接字来实现TCP式或UDP式的工作方式。

对开发者的好处

  1. 开发者可以通过管理套接字文件的访问权限来管理Unix域套接字的访问权限。也就是说,不能访问某个套接字文件的进程,也就不能使用该套接字。
  2. 因为Linux内核与Unix域套接字通信并不需要经历网络层次,所以性能会比网络套接字好。

为Unix域套接字写代码跟支持一般的网络套接字没多大不同。因为它的好处十分明显,所以有些网络服务器会同时提供网络套接字和Unix域套接字的连接。例如,MySQL的数据库服务器mysqld能接受远端的连接,同时也以/var/run/mysqld/mysqld.sock提供Unix域套接字。

列出Unix域套接字

你可以使用lsof -U来查看系统正在使用中的Unix域套接字:

# lsof -U
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
mysqld 19701 mysql 12u unix 0xe4defcc0 0t0 35201227 /var/run/mysqld/mysqld.sock
chromium- 26534 juser 5u unix 0xeeac9b00 0t0 42445141 socket
tlsmgr 30480 postfix 5u unix 0xc3384240 0t0 17009106 socket
tlsmgr 30480 postfix 6u unix 0xe20161c0 0t0 10965 private/tlsmgr
--snip--

Linux——网络应用与服务相关推荐

  1. linux下启动nfs服务,linux下Samba服务和NFS服务配置的方法

    linux下Samba服务和NFS服务配置 一.Samba服务配置过程 samba的功能很简单,就是为了使linux和windows之间能够实现共享.并且利用samba搭建文件服务器,不仅比windo ...

  2. Linux下网络服务的安全设置

    Linux下网络服务的安全设置 Linux操作系统由于其良好的稳定性.健壮性.高效性和安全性.正在成为各种网络服务的理想平台.各种网络应用在Linux系统上部有性能卓越的应用,例如,提供Web服务的A ...

  3. linux 从命令行启动,Linux下常见服务在命令行方式的启动

    昨天下午正在超市购物,BOSS打电话问我会不会配置Linux下的samba? Samba是Linux下提供的类Windows下"网络邻居"的服务.一般只有启动的时候安装了才可以启用 ...

  4. 如何查看和停止Linux启动的服务

    http://blog.chinaunix.net/uid-16844439-id-3241471.html 1. 查看Linux启动的服务 chkconfig --list 查询出所有当前运行的服务 ...

  5. Elasticsearch官档翻译——2 2 在Linux上启动服务

    #在Linux上启动服务 为了在Linux上启动ES服务,官方提供的包尽可能让你在升级或重启集群的时候轻松地启停集群. 目前我们有构建debian和rpm两种安装包,都可以在下载页获取.包本身没有依赖 ...

  6. linux追踪tomcat报错信息,linux下tomcat服务的启动、关闭与错误跟踪

    linux下tomcat服务的启动.关闭与错误跟踪,远程连接到服务器以后,通常通过以下几种方式启动关闭tomcat服务: 1).启动tomcat服务 进入tomcat主目录下的bin目录,然后执行如下 ...

  7. linux下tomcat服务的相关命令

    2019独角兽企业重金招聘Python工程师标准>>> 一:Linux下tomcat服务的启动.关闭与错误跟踪,使用PuTTy远程连接到服务器以后,通常通过以下几种方式启动关闭tom ...

  8. linux rpc.statd服务 获取系统性能统计 简介

    大家在安装好RHEL/CentOS系统后,用netstat查看及端口情况,可能会发现有个rpc.statd服务,是不是不知道是哪个服务启动的啊?如何关掉RHEL/CentOS的rpc.statd服务呢 ...

  9. kali linux ssh不要密码登录密码,kali linux 登录ssh服务常见问题

    kali linux 登录ssh服务常见问题 kali linux 登录ssh服务常见问题 kali linux 登录ssh服务常见问题 一.ssh简介 1.层次 2.ssh解决问题 二.服务器发送了 ...

最新文章

  1. 【 C 】字符分类函数
  2. HDU 5693 D Game 区间dp
  3. markdown-Macdown
  4. P5712 【深基3.例4】Apples(python3实现)
  5. android-studio add jar
  6. 魅族17 Pro通过3C认证:魅族史上最强快充
  7. Spring : ImportBeanDefinitionRegistrar源码分析
  8. 数据结构上机实践第八周项目4-字符串加密
  9. bookstore项目学到的对象
  10. java中的implements如何打开_Java 中extends与implements使用方法
  11. 产品设计:《设计美学》
  12. 信息搜集方法小结(持续更新)
  13. 如何查看内存条的实际使用频率
  14. 直方图python_Python数据可视化的例子——直方图和核密度曲线
  15. enterprise architect mysql_Enterprise Architect 8之数据建模(创建表) | 学步园
  16. 浅谈几个倾斜摄影三维模型的修补软件
  17. CSS常用英语词汇大全
  18. MSSQL2019+Linux7, The SQLServerAgent is not currently running, so it cannot be notified of this
  19. 虎牙、斗鱼同道同命:共同御寒
  20. 使用PySide2创建图形化Python程序时:Available platform plugins are: direct2d, minimal, offscreen, windows

热门文章

  1. 摩托罗拉多开助手by IM大朋友
  2. 外文网站对CMap用法的精辟解释
  3. 珠三角地区调查研究咨询市场知名公司信息情况
  4. Valgrind使用简介
  5. 计算机监控系统功能概述,物联网技术在计算机监控系统的应用
  6. Maple、MATLAB、MathCAD和Mathematica
  7. windows下的wsl-kail
  8. outlook2007 菜单灰色...不能使用的解决方案
  9. 经典机器学习算法:高斯判别分析GDA
  10. [ASP.NET]文件处理