基础介绍

Uniswap是一个用于以太坊上自动代币交换的协议。它围绕易用性、gas使用效率、抗审查性和零抽租而设计。其主要特点是抛弃了cex的订单簿交易方式,采用设计的恒定乘积做市商机制。2020年9月发行了代币Uni。

经济模型

发行状况

uni的初始创世总量为10亿枚,初始量会在4年内按照每年2%的通货膨胀增发,确保Uni持有者能继续在Uniswap中参与和贡献。初始发行的Uni按照60%在社区,21.66%给团队,18.044%给投资人,0.69%给顾问的分配方案。后三者都设置了4年的锁仓期。

分配情况

其中社区的6亿枚空投给1.5亿老用户,通过4个池子各500万的流动性挖矿奖励释放完成,剩余4.3亿枚也将通过逐年递减的方式在4年释放完成。

关于获得和用例

Uni作为治理token,这些token的持有者都可以参与社区提案或投票,决定协议的运作方式。Uni没有协议使用费用,并且Uni的4个流动性挖矿的池子已于2020年11月停止挖矿。

uniswap机制

1、消耗机制

  • 当LP为流动池提供流动性时,会返还LP token。当LP赎回流动性时,就会销毁提供的token。
  • 赎回流动性时会扣除0.3%的手续费。
  • Uniswap v3为LP提供了四种不同的手续费收费标准——0.01%、0.05%、0.30%和1.00%。
  • 通常情况下,LP会按照目前流动性池里代币的比例来增加流动性,获取LPS。如果新质押的代币比例与流动性池中不一样,会按照token数量少的来等比例质押,另一种多出来的不会去质押,避免损失。如果是直接去操作Pair合约,否则还是按token数量少的计算LPS,另一种多出来的将作为捐赠。

2、奖励机制

  • LP为每个交易对提供流动性,维持这两种资产的乘积不减少。LP将按提供的流动性的比例获得每笔交易的手续费。
  • 在V1的基础上,Uniswap v2引入了协议费用开关。交易费用将设置为名义交易量的0.3%,收取的费用分配到池的储备金中。开启协议后,Uni持有者将收取每次交易手续费的0.05%,而LP的奖励将降低至0.25%。
  • Uniswap V3中,用户可以参照所有个人曲线接合的流动性进行交易,且每个流动性提供者的gas费都不会增加。LP按一定价格区间收取交易费用,并按照他们在该区间贡献的流动性数量按比例分摊。

3、底层机制

  • Uniswap的底层机制概述

    不需要传统的订单簿,也不需要对手盘。通过恒定的计算公式,让智能合约来做市商进行交易。在每个交易对中,两种代币X和Y的资金量决定了价格。在$x * y = k$**(k为常数)**公式中,维持k不变。x的数量越多,y的数量越少,相应的该交易对中x的价格也会降低,y的价格会上涨。

  • V1

    Uniswap V1建立了存储A和B两种货币资产的供给池。用户在用A兑换B的过程中,用户的A会发送到供给池,使供给池中的A增多,同时,供给池的B会发送给用户。而A和B的兑换之间的汇率(定价)会根据$**x * y = k$ (k为常数)**公式自动定价,通过供需关系实现自动调价。

  • V2

    1. 自动做市

      V2中在V1的基础上增加了机制自动化做市商(Automated Market Maker,AMM)。用x从流动性池中交换y,假设输入x的量为deltax,交易换回的y为deltay,在交易池中的资产足够的前提下,满足:

      $(x +delat x) *(y-deltay)=k$(其中delatx,delaty等为微小变量)

      $delta y = y – k/(x+deltax)= deltax * y/ x + deltax$

      就是指交易前后,流动性池中两种代币的乘积是恒定不变的。因此,如果交易的量相对于流动池中的量很小的话,那么交易价格就近似为当前两种代币的比:

      $price(y) = deltax/deltay = x/y$(近似于)

    2. 去中心化预言机

      Uniswap v2推出了时间加权平均价格(TWAP)的预言机。V2 预言机通过累计以每秒为基础存储Uniswap交易对价格总和来工作。这些价格总和可以在一个时期的开始和结束时检查一次,以计算该时期的准确时间加权平均价格(TWAP)。

  • V3

    1. 集中流动性

      在v3中,LP可以将资金集中在自定义的价格范围内,并在期望的价格上提供更多的流动性。这样一来,LP就能构建出反映自己偏好的个性化价格曲线。这样LP可以将自动化做市商形态和订单簿形式做到近似。用户可以参照所有个人曲线接合的流动性进行交易,且每个流动性提供者的gas费都不会增加。LP按一定价格区间收取交易费用,并按照他们在该区间贡献的流动性数量按比例分摊。

    2. Architectural Changes 架构变动

      Uniswap v3为每个交易对引入了多个池子,允许分别设置不同的交易手续费。所有池子都使用相同的工厂合约创建。默认允许创建三个手续费等级:0.05%,0.30%和1%。可以通过UNI治理添加更多手续费等级。

    3. Governance 治理

      工厂合约拥有一个owner(一个TimeLock合约),该地址初始时被UNI代币持有者控制。owner没有权限暂停core合约的任何操作。UNI治理有权利将owner转移给其他地址。

    4. Oracle Upgrades 预言机升级

      1. Uniswap v3无需预言机用户在外部记录历史累计价格。v3将累计检查点放到core合约,允许外部合约直接计算最近一段时间的链上TWAP,无需额外保存累计价格。
      2. Uniswap v3不再使用累计价格之和计算算术平均数TWAP,而是通过记录$log$价格之和计算几何平均数TWAP。
      3. Uniswap v3还增加了一个流动性累计数,每秒累计L分之一(即流动性倒数)。累计流动性对于那些基于Uniswap v3实现流动性挖矿的外部合约很有用。它也可以被其他合约用于判断一个交易对的哪个池子具有最可信的TWAP。
  • 其他机制

    1. 维持流动性机制(Uniswap V2)

      Pair智能合约对应的LPS是有18位小数的(以太坊中最大的小数位数),理论上有一种情况是LPS的最小量Minlps(即0.000,000,000,000,000,001 LPS)价值非常大,导致后续小流动性提供者很难再提供流动性了,因为提供流动性的成本太高了,例如Minlps = $100的,要增加流动性就至少质押$100美金才能获得LPS,而随着LPS增值,流动性成本越来越高,不利于维持交易的流动性。在Uniswap白皮书中把这种极端情况认为是一种可能的人为攻击,为了提高这种攻击的成本,在新创建流动性池的时候,设置了最小流动性值Minlps15=0.000,000,000,000,001,即LPS最小单位的1000倍,任何流动性池在启用之初都要在零地址中锁定Minlps的LPS。

      维持流动性机制之下,如果人为把LPS价值提升到Minlps = $100,就需要在零地址中锁定价值 $100,000 的LPS,这样就极大地提升了攻击成本。而且在通常情况下,Minlps15的价值是很小的,甚至可以忽略,所以第一次质押后获得的LPS虽然要减少Minlps15,但约等于10,000不变。

    2. Pair的流动性跟踪机制(Uniswap V2)

      在初始化一个pair合约之后,其中两种代币的初始值为0,为了使流动性池可以开始促成交易,必须有流动性提供者(LP)质押移动量的两种代币来启动流动性池,第一个LP就是这盯着流动性池初始价格的人,并且获得流动性池份额(LPS)。每次交易完之后由于两种代币的数量会发生变化,价格会遵循自动定价公式,将LP初始化质押的两种代币量分为X0和Y0,则获得的流动性池份额(LPS)为s0:

      $S0^2 = X0 * Y0$

      这样的计算的好处是可以是LPS在任何时候都不受质押的两种代笔的比例影响,因为两种token在流动性池中的比例可能与市场价格不符。

      按照LPS初始值的计算公式,一个LPS的价值不会低于Pair中两种质押代币的几何平均数,而且随着交易手续费的积累会使LPS的价值升高,因为交易手续费在流动性池中积累,针对这部分手续费并不会产生新的LPS,效果就是池子变大,但是LPS总量没变,两者的比值即LPS的价值就升高了。

    3. 无常损失(Uniswap V2/V3)

      这种损失是由于代币价格背离引起的。当价格回归时,这种损失也就没有了。损失不等同亏损。当一对代币存入Uniswap后,如果一种代币以另一种进行计价的价格上升,那么在价格上升后你把他们取出,得到的总价格比直接手握这两种代币要低一些,低的这一部分就是损失,价格偏离越大损失就越大,所以可能造成亏损,特别是当两种代币在实际中都要以其他稳定币来计价时。

    4. Uniswap V2 ERC20优化AMM机制

      Uniswap V2 ERC20要求owner在链下对某个Dapp授权操作的签名,将其一起发给DApp的智能合约,在DApp智能合约中发起的ERC-20的执行交易中,先验证授权签名,然后再调用提取函数进行owner账户下的token提取,这样整个交易流程就只有一个链上交易,将大幅降低gas费。

      Uniswap V2 Pair主要提供了三个功能:

      1. 流动性追踪

        追踪交易池中的代币余额,并且提供流动性代币。

        流动性:指合约里的两种ERC-20代币的综合,同时质押两种代币称为增加流动性。

        流动性池(Pool):所有流动性汇集成的池子,即AMM的资产池,Uniswap协议通过流动性池提供个人对合约的交易撮合。

      2. 流动性提供者(Liquidity Pool / LP)

        Uniswap V2 Pair本身也是一种ERC-20合约,它的代币用来作为流动性代币,在LP提供流动性时自动增发(mint)代币给LP,提供流动性时燃烧(burn)LP的代币。

      3. 流动性池份额(LPS)

        计算所占有的流通的流通型代币的份额值,用来记录每个LP的流动性贡献比例。

投票治理过程

  • Uniswap 的提案流程

    发起人/团队进行社区民意调查→发起人/团队发起提案→委员会进行审核→投票环节→提案通过,发起人/团队获得资金或其他支持→完成提案,验收。

  • Uniswap 持有者提交提案

    任何地址中持有超过 2,500,000 个 UNI 可以提交修改或引入新功能的提案,并获得其他社区成员的批准。UNI 持有者可以自己投票或将他们的投票委托给其他用户,持有者认为他们会做出代表 Uniswap 生态系统最佳利益的决定。

    • 第一阶段是温度检查,提议者需要向社区介绍想法并获得足够的选票以进入下一阶段。在这里,该提案必须获得多达 25,000 个 UNI 赞成票才有资格进行进一步审议。
    • 第二阶段是共识检查。在这个阶段,提议者必须启用正式的讨论,以突出提议的核心变化和优势。对于扩大这一阶段的提案,提案必须吸引不少于 50,000 个 UNI 的赞成票。
    • 第三阶段是治理提案。这是提议者提交经过审计的代码以进行最终审议的地方。与其他两个阶段一样,有一个最低投票要求来决定提案是否被采纳——每个提案必须获得多达 40,000,000 个 UNI 赞成票才有资格实施。

版本的区别

  • V1&V2

    1. V2支持ERC20 token/ERC20 token交易对

      v1使用ETH作为过渡货币,每个交易对都包含ETH。这使得路由更简单(不同token之间都要进行与ETH的转换进行),并且减少了流动性的分散。但所有LP都有ETH的敞口,增加了LP的成本,并且由于其他资产相对于ETH的价格而变化遭受无常损失。使用ETH作为强制性过渡货币也会给交易者带来成本。交易者必须支付的费用是直接购买交易对的两倍费用,因此会遭到两次滑点。

    2. V2强化的价格预言

      合约无法知道用户想要哪个资产作为账户单位,所以会同时追踪两个价格;用缓存的资金储备更新价格预言而不用当前资金储备。

    3. 快速互换

      允许用户在支付前接受和使用资产,只要他们在同一个原子的转账中完成支付。swap函数调用一个可选的用户指定的回调合约,在这之间转出用户请求的token并且强制确保不变。一旦回调完成,合约检查余额并且确保满足不变(在经过支付手续费调整后)。如果合约没有足够的资金,它会回滚整个交易。用户也可以用同样的代币返还给Uniswap资金池而不完成互换。这高效地让任何人从Uniswap资金池快速借取任何资产(Uniswap收取同样的0.3%的交易手续费)

    4. 协议手续费

      Uniswap v2包括0.05%协议手续费,默认情况下是关闭的。打开后手续费会被发送给工厂合约中制定的feeTo地址。初始时,feeeTo没有被定义,不收手续费。一个预先指定的地址feeToSetter可以在Uniswap v2工厂合约上调用setFeeTo函数,设置feeTo地址。feeToSetter也可以自己调用setFeeToSrtter修改feeToSetter地址。如果feeTo地址被设置,协议会收取0.05%的手续费,从流动性提供者的0.3%手续费中抽取1/6.交易者将在所有交易商支付0.3%手续费,83.3%的手续费给LP,16.6%手续费给feeTo地址。总共收集的手续费可以用自从上次手续费收集以来的增长来计算。

  • V2&V3

    1. Layer 2中的Uniswap

      因以太坊交易费的增长,个体用户在使用Uniswap面临巨大的经济压力。而v3将部署在“Optimistic Rollup”的Layer 2扩展解决方案中。这可以在扩展智能合约的同时享受以太坊网络的安全性。该部署应该会推动交易吞吐量大幅增长,用户的交易费用也会显著降低。

    2. Non-Fungible Liquidity 不可互换的流动性

      在Uniswap v3,由于头寸的不可互换性,复利将变得不再可能。相反,手续费被独立保存,并且以支付手续费的代币形式持有。由于每个头寸的价格区间都不一样,因此v3的流动性不再像v2一样分布在所有价格区间,也就是说,v2流动性是可互换的,因此可以使用ERC-20代币表示。而v3流动性实际上是一个NFT(不可互换代币),使用ERC-721 表示。

    3. 移除原生流动性代币 。在Uniswap v1和v2,交易对池子合约本身是一个ERC-20合约,它的代币表示池子持有的流动性。Uniswap v3引入的改动让可互换的流动性代币变成不可能。由于自定义流动性的特性,现在手续费以独立的代币被池子收集并持有,而不是自动复投为池子的流动性。

uniswap的审计公司介绍

  • ConsenSys Diligence

    母公司是ConsenSys,该公司作为知名以太坊软件公司。旗下有Infura、Quorum、Truffle、Codefi、MetaMask和Diligence。

    1. 提供的服务

      智能合约审计、自动化安全分析、智能合约测试、自动属性检查、企业安全咨询、威胁建模、时间响应计划

    2. 审计报价

      根据合约项目制定一对一方案

    3. Uniswap合约完整审计报告

      GitHub – ConsenSys/Uniswap-audit-report-2018-12

    4. 该公司审计的其他重要合约

      ENS、AAVE。liquality

      更多参考下面链接:

      Public Smart Contract Audits and Security Reviews | ConsenSys Diligence

关于Uniswap的思考

  • Uniswap v2中滑点过大,夹子问题

    1、什么是夹子

    机器人通过检测Uniswap所有交易对寻找滑点利润,当机器人检测到大额挂单后通过提高gas来提前买入抬高价格,随后再出货从而实现利润。

    2、具体操作

    整个流程最核心的操作就是在交易对中出现大额买卖,将引起价格剧烈波动时,夹子机器人抢先交易,从而实现利益最大化。而这个操作的前提是大额交易,由于恒定乘积公式的原因,池子中出现大额的交易,会影响池中代币价格剧烈波动。

    3、解决方法

    综上,解决这一问题的办法就是避免大额交易,根据池中的总额度选择适当的金额进行交易;若有大额交易需求,可以分为多笔进行交易,这虽然会产生多笔gas费,但是相较于被夹子套利来讲,多笔交易产生的gas费是可以接受的。

    4、坏处

    将对用户造成巨额损失,降低用户使用积极性,减少Defi的交易活跃度。

    5、好处

    使交易者不会贸然进行大额交易,能使交易对在合理的区间波动,避免致使池子流动性枯竭。

  • Uniswap2中快速互换机制,出现闪电贷操作

    1、什么是闪电贷

    因为Uniswap v2增加了快速交换机制,这样就导致出现了在传统的金融市场中不可能出现的操作——闪电贷。顾名思义就是快速的借贷还贷,而无需任何的抵押物。

    2、具体操作

    在Uniswap中实现闪电贷,首先套利者需要找到有价差的交易对,然后使用A代币到交易对中贷出B代币,再将B代币用于另一个交易对贷出代币C,随后将代币C置换回代币A,最后在保证和贷出时的交易块是同一个区块的前提下将贷出额度进行偿还,整个流程结束。套利者获得中间的价差,而成本只是交易中产生的手续费。而贷出额度越大。交易的交易对越多,获利越多。

    3、解决方法

    闪电贷的交易条件很苛刻,要求有大额的资金、足够的套利空间交易对、需要在一个区块中完成多笔交易、最后需要有足够的资金偿还贷款金额。如果这其中一个环节失败都将会导致交易回滚,损失gas交易费。因为uniswap机制的缘故,又有大量的人涌入这个操作中,出现为了保证交易链的完整性,需要用更多的gas费来贿赂矿工,最后套利者收益减少,更多的收益流到了矿工手上,这导致了很多人放弃该逐利操作。也能通过提高预言机价格获取延迟和增加交易延迟。

    4、坏处

    若出现预言机攻击,导致价格在短时间内出现错误,使套利者借出更多的钱,这将对LP造成巨大损失;大量的闪电贷交易会引发gas war,这不利于后续交易者交易,降低人们交易需求;使真正有借贷需求的用户没有足够额度,减少LP收益。

    5、好处

    持有一个可清算的借款头寸,实现链上清算,加强资金流动;快速铸造ERC20的代币,需在区块结束时销毁代币;铸造新的代币进行抵押物替换。让池子中代币的价格回到正常值。

Uni v2套利流程:

代码分析:

Uinswap V3 主要由工厂Factory合约 池子Pool合约组成。加路由合约 (工厂会部署很多不同的池子)

  • factory

工厂定义了生成池的逻辑。池由构成资产对的两个代币和费用定义。同一资产对可以有多个池,仅通过交换费用来区分

  • pool

矿池主要作为配对资产的自动做市商。此外,它们公开价格预言机数据,并可用作闪存交易的资产来源。

  • router

交换路由器支持前端产品交易的所有基本要求。它本身支持单次交易(x 到 y)和多跳交易(例如 x 到 y 到 z)