interledger / rfcs

Specifications for Interledger and related protocols
https://interledger.org
Other
427 stars 106 forks source link

Interledger amounts should be of type UInt128, not UInt64. #385

Closed felixvf closed 6 years ago

felixvf commented 6 years ago

Interledger amounts should be 128 bits wide, not 64 bits wide.

The current draft spec mandates that

the amount is counted in terms of the smallest indivisible unit on the receiving ledger.

If we take the example of Ethereum, its smallest indivisible unit is the "Wei".

Let's ask: What amounts may be transferred over such a ledger?

Let's take a conservative estimate that the amount to be transferred is bounded by the maximum amount available: The current Ethereum supply is around 100000000 Ether, which hence is the bound. This number equals to 100000000000000000000000000 Wei. This number is 0x52b7d2dcc80cd2e4000000 (in hexadecimal) Wei and 0b101001010110111110100101101110011001000000011001101001011100100000000000000000000000000 (in binary) Wei.

Note that this number is already 88 bits long, and thus far exceeds the amount of bits offered by the current draft of the Interledger Protocol.

Note that already the value of 19 Ether equals to 0b10000011110101101100011110101010101101100011011000000000000000000 Wei, which is already 65 bits long and thus too much for the current draft of the interledger protocol. Also note that 19 Ether may be at market value of less than 19 USD (as has happened for EthereumClassic, which had – at times – a market value of less than 1 USD/ETC).

Hence, it may happen that a particular Payment Packet may not be able to represent a higher value than the equivalent of 20 USD (or maybe just 0.01 USD, depending on the market value of the smallest indivisible unit of the ledger involved).

Is that intended?

(Is there a requirements document outlining the minimum and maximum value in terms of a currency which has higher stability over time (e.g. USD), and a rationale for why these minimum and maximum values are chosen?)

I guess this low limit is not intended.

We should aim for a much higher maximum value representable by a single Payment Packet.

A workaround is ugly

It is possible to work around this limit by encoding a different convention on the unit used in the destination account field of the Payment Packet. But this is a hack, because it explicitly reuses the amount field for a different thing than is designed for, and this hack needs to be standardized over many connectors dealing with this new type of destination account, lest the Payment Packet may not get delivered. But even if there was a standard standardizing to "interpret" the Interledger Protocol differently than intended, it would show clearly a mismatch between the original standard and application.

What happens when workarounds become standard?

IPv4 had such a design error by erroneously assuming – at design time – that there might be no more than 232 internet hosts (even though, at that time, human population already exceeded 232 and mobile device usage was already imagined) and therefore 32 bits shall be enough for an IPv4 address. When these problems became apparent in the late 1990ies, we should have gotten IPv6 (and therefore 128 bit IPv6 addresses). But what we actually got was Network Address Translation. However, NAT, since its inception, gives every implementer of protocols over IPv4 and even many users headaches, as it breaks

  1. the end-to-end principle and
  2. protocol layer isolation (Routing is a matter of IP. Hence, routing should be dependent just on the destination address, not on some field in some upper layer protocol on top of IP.).

Have you ever been bothered with issues such as

  1. "You need to open this port?",
  2. "You need to configure this STUN server, else SIP calls fail, but only sometimes.",
  3. "UDP hole punching",
  4. "TCP hole punching",
  5. "The open chat standard, XMPP, is dying because there are no decentralized solutions for pushing messages from an XMPP server to mobile phones without requiring the phone to regularly send keep-alive packets, draining the battery. You need to use Apple Push Notification Service. Restrictions apply. "
  6. "Innovative protocols, such as SCTP, are not usable in practice.", "Workarounds are tried."
  7. "Why aren't people hosting their pages (e.g. Facebook page) on their own device (e.g. their mobile phone) (and instead give up their privacy to the point that younger people nowadays do not understand what "privacy" means)? Because hosting on your own mobile device is impossible due to NAT, both when using mobile data (due to NAT at the mobile carrier) and when at a fixed location (due to NAT at the place's router)."

?

This is what NAT gave us. This is what properly designed IPv4 (with 64 bit addresses instead of 32 bit addresses) would have avoided.

NAT is considered harmful., but we got NAT anyway, due to the too-limited design of IPv4, and it will apparently never die out in favor of IPv6, due to the limited-yet-good-enough-for-some-purposes design of IPv4.

The Interledger Protocol should not repeat similar epic design errors by wrongly sizing its fields.

What what is the proper width for the amount field?

Interledger amounts should be able to be both large and small. To be truly interoperable, we should ask ourselves what "large" and "small" can be. As outlined, we should be very cautious here.

Maximum value

The proper maximum value should be guided by the highest conceivable value in the world. Which is the value of the world. However, this amount was not easily available.

We can also try to estimate a bound of the value of all products of the world. We can ask "What would be the steady state value of all products in the world if the whole population was producing these and the products had the lowest depreciation rate and the population had the highest productivity?". Take the highest GDP per capita of a country (e.g. 105000 USD per capita in Luxembourg), divide it by the lowest depreciation rate for products (which is buildings: 2% per year), and multiply it by the expected parallel amount of humans (which is 11000000000), and the bound is: 57750000000000000 USD.

Minimum value

The proper minimum value should be guided by the lowest conceivable non-zero value in the world, or at least the lowest non-zero value to be transmitted over the Interledger Protocol. Which is the value of the transmission of one bit. (It sounds implausible that the Interledger Protocol will be used for payments with a lower value than the cost of transferring the payment data.) One bit of worldwide traffic costs currently about 0.000000000000130 USD (A hosting company currently asks for 1 EUR per TB traffic, including VAT.) However, it is likely that this price will drop further, as the amount of traffic is roughly doubling every year.

Spread

The current spread between the minimum and the maximum value is about 99 (≈log(57750000000000000/0.000000000000130)/log(2)) bits. That is, if a ledger designer would optimally pick a smallest indivisible unit with a market value of 0.000000000000130, it would need 99 bits to represent the market value of 57750000000000000 USD.

However, usually, ledger designers cannot pick such a value easily, because they may not know the maximum market value of their currency in advance, and because market values of currencies vary widely and wildly (Bitcoin's market value minimum and maximum was about 0.07 USD and about 20000 USD so far, which means a spread of about 18 bits.). Hence, some leeway should be provided.

Additionally, as the price of transmission of one bit of data continues to drop like it did in the last decades, in less than 19 years, the price of one bit may be lower than 2-128 times the highest conceivable value in the world, bringing even 128 bit amount fields to their limit. However, it is not clear whether the transmission prices will change by factor 2-19 in the foreseeable future, as fiber optic cables may have maxed out their potential before reaching that price and alternatives are not in sight.

Conclusion

While 100 bits seem to be sufficient now, for practicality and for leaving room for the future, 128 bits should be the lowest proper width of the amount field of the Interledger Protocol, at least for the next 19 years. A width of 64 bits is already too low now, and even less future-proof.

256 bits?

I would not be opposed to 256 bits, which would be more future-proof and which would obtain complete compatibility with Ethereum style blockchains and Ethereum style tokens, but even for Ethereum, I consider 128 bits as sufficient, as 18 decimal places seem to become customary, and 128 bits roughly translates to 38 decimal digits.

However, 256 bits would likely meet more resistance, and 128 bits seems to avoid almost all of the interoperability problems for the foreseeable future and for all foreseeable applications of the Interledger Protocol.

What are the downsides of using 64 bits?

  1. All conceivable values of all ledgers cannot be transferred within one Payment Packet.
  2. Stretching the payment over multiple packets may be used as a workaround, and that workaround may become mandatory. However, the latency of the Interledger Protocol may make stretching a payment over millions of packets uneconomical, restricting its usefulness.
  3. The protocol could be abused by encoding the meaning of the amount field in the destination account field in order to have a workaround. However, this is an invitation for incompatibility, as sketched above, and implementation bugs. ("You say you sent me 3 ETH? I just received 0.000000003 ETH.")
  4. The Interledger Protocol never reaches its full potential, but because it is "good enough" for many applications, better versions of the Interledger Protocol will be out-competed by the then-incumbent worse version of the Interledger Protocol, preventing innovation and utility (as NAT did to IPv6, XMPP and SCTP).

What are the downsides of using 128 bits instead of 64 bits?

  1. We need 8 bytes more per Payment Packet. This should not be a concern given the computing power of the machines of today, tomorrow (and even yesterday). Even the smallest of them will be able to physically handle the 8 bytes more.
  2. We need 128 bit arithmetic in Interledger Protocol implementations. Actually, we do not: Implementations could restrict themselves to 64 bit implementations and reject Payment Packets with higher amounts using a "F07 Cannot Receive" final error.

What are the upsides of using 128 bits instead of 64 bits?

  1. All conceivable values of all ledgers can be transferred within one Payment Packet. Stretching the payment over multiple packets is not mandatory. (If it was mandatory, as with 64 bits, the latency of the Interledger Protocol may make stretching a payment over millions of packets uneconomical, restricting the usefu.)
  2. There will be no need for workarounds for ledgers, currencies and tokens with a lot of decimal places (such as Ethereum, Ethereum Classic and all their tokens).
  3. The Interledger Protocol does not need to change in the foreseeable future (and thus provides much higher utility than if there was a need for replacement or workarounds).
  4. The Interledger Protocol could replace the Internet Protocol. (For example, the Interledger Protocol could solve the DDoS and the spam problem if traffic was going over the Interledger Protocol instead of over the Internet Protocol: The Interledger Protocol may allow receiving hosts to set a price for delivery of data. Receiving hosts may raise the price for delivery if they are spammed, and lower the price for "known" or "welcome" users. This would allow the removal of captchas from the user's internet experience (and – for that matter – the removal of ads as well). Users just "charge" their internet client little bit and if consumption is higher than expected, users could investigate why consumption has increased. Was it that expensive website with high-valued content and no ads? Or was it a trojan unwanted software performing DDoS for nefarious purposes?) But this only works if the Interlegder Protocol supports very small values.

Conclusion: Interledger amounts should be 128 bits wide, not 64 bits wide.

What do you think?

@emschwartz You asked me about 1 month ago to make a case for this, so what do you think?

sharafian commented 6 years ago

The choice of 64 bits is more about precision than scale. 64 bits provides ~20 digits of precision. The scale is unlimited, because the scale is just based on the context of what ledger you're on.

You're right that this means we can't have a single packet for 100000000.000000000000000001 Ether. But you could still have a packet for 1e8 Ether, or a packet for 1e-18 Ether, because both of those are easily within the precision limits of an ILP payment.

Our reasoning in choosing 64 bits is that if you're receiving $100000000, then an additional $0.000000000001 is not significant. We're talking about someone sending a billion-dollar payment and complaining when they're short by a single nano-dollar.

Hypothetically if you needed less than %0.000000000000000001 error in your amounts, you could open two accounts. One of these accounts is denominated in atto-dollars, and another is denominated in dollars.

Only the connector with whom these accounts are held needs to understand the scales. To anyone else on the network this is opaque: it's not even end-to-end because the sender doesn't need to understand the receiver's units. As a sender I don't need to understand the difference between mUSD and nUSD any more than I need to understand the difference between ZAR and CNY. Senders and connectors only need to understand the units of the systems they actually hold accounts on.

You can then split your $100000000.000000000001 payment into two packets. The number of payments is related logarithmically to the amount: even an amount that uses the whole 256 bits of an Ethereum amount could be split into 4 payments.

The much larger challenge in this scenario is constructing a network that is capable of routing payments that are different in size by a factor of more than 10^19.

adrianhopebailie commented 6 years ago

@felixvf can we close this?

felixvf commented 6 years ago

@sharafian But how is the scale specified?

When paying an exact Ether sum, 4 packets with different scales may be needed, agreed. But how would these 4 packets with different scales look like? Is there any standard on specifying the scale?

When "3" units are sent to g.crypto.ethereum.0x20f5beb5c3858433633f53f8e08c5da19d17516e, what does arrive (or what should have arrived)?

  1. 3 ETH
  2. 0.000000003 ETH
  3. 0.000000000000000003 ETH

Likewise, when "7" units are sent to g.crypto.rcl.xrp.ra5nK24KXen9AHvsdFTKHSANinZseWnPcX, what does arrive (or what should have arrived)?

  1. 7 XRP
  2. 0.000007 XRP

Until these questions of scale are not answered (and specified) in a crystal clear way for every ILP address, do you reasonably expect that you will not see a stream of reports "I wanted to receive 20000 USD worth of some currency using the Interledger Protocol, but have just received 0.02 USD worth of it. No one told me that the scale is different from what I expected, and now the money is gone."?

You could claim that specifying the scale is out of scope of the Interledger Protocol itself, but then it should to be in scope somewhere else, for example at the ILP Addresses spec. (But I do not see that there.) So where is the scale in scope?

(Just my twenty thousand dollars^W^W^Wtwo cents.)

sharafian commented 6 years ago

I think we have a misunderstanding around ILP addresses, which is understandable given how we used to give example ILP addresses vs. how we now give them.

On ILPv1, the prefix of a ledger (i.e. g.crypto.ethereum.) would be chosen when you implement a plugin. When you implement a plugin you also would choose the scale that it uses. If someone implements a different plugin they would need to either make it compatible (use the same prefix, scale, protocols, etc.) or use a different prefix so that peers using the other plugin won't get confused.

This style of addressing no longer makes sense when the network is based around bilateral relationships, rather than large multi-lateral systems. So in ILPv4 you won't see addresses like g.crypto.ethereum. because there isn't a single place in the network where Ethereum lives. Thousands of different people could be settling over Ethereum, but that only matters to the two parties on each of those bilateral links.

So if my address is g.some_ilsp.sharafian, I decide the scale and settlement mechanism with my ILSP. It's not encoded in the address or any standard, it's just a configuration option in our bilateral agreement.

Hope this clears things up