Introduction
Despite being introduced by Goldwasser et al.1 as far back as 2008, the GKR protocol and its line of work remain among the most popular verifiable computation protocols today. In the Virgo++2 paper by Zhang et al., the authors introduce a method to execute the GKR protocol for general circuits with linear proving time. In this post, we will discuss the techniques mentioned in the paper and provide some intuition on how they work. We encourage the readers to read the paper for further insights and to gain a complete view of the material mentioned in this blog post.
Improved Protocol
Before we dive into each of the changes, let’s take a look at the improved protocol to gain an overview of how it works. If you are already familiar with the original GKR protocol, you will notice that it looks almost the same. The main differences are:
- The equations for each layer have been replaced with Equation 3.
- The method for combining claims is implemented using a sum-check protocol as outlined in Equation 5.
- Use the linear time sum-check algorithm.
Here’s a simplified view of Protocol 3 from the paper:
- Define the function and compute the claim for the output at the layer
- Define the multilinear extension of the circuit output as .
- The verifier picks a random and send it to the prover.
- Both the verifier and the prover compute .
- Round
- The prover and the verifier run the sum-check protocol on Equation 3 for layer .
- The verifier checks that is the same as the prover’s claim in the last round of the sum-check protocol.
- The verifier now has the claims from the subsets of gates from all the layers connecting to layer .
- Round
- Combining the claims from the previous layer
- The verifier picks random values and send them to the prover.
- The prover and verifier run the sum-check protocol on Equation 5 to combine the claims.
- if , run the sum-check protocol on Equation 3 for layer
- The prover and the verifier run the sum-check protocol on Equation 3 on the combined claims for layer .
- The verifier checks that is the same as the prover’s claim in the last round of the sum-check protocol.
- The verifier now has the claims from the subsets of gates from all the layers connecting to layer .
- Combining the claims from the previous layer
- Verify the input of the circuit
- The verifier is left with a claim of on the last layer , .
- The verifier can compute it locally or ask the oracle to verify the claim.
Let us now take a closer look at each of the changes.
Problem with GKR
One of the significant limitations of the original GKR protocol is that it can only work with layered arithmetic circuits. While in theory, any computations can be represented as a layered circuit, in practice, most computations are better represented as a general arithmetic circuit. Although a general circuit can be converted into a layered circuit by adding relay gates, this leads to a few problems:
- The circuit size increases by a factor of (the depth of the circuit)
- The prover time also increases by a factor of , i.e.
- Common use cases, such as R1CS circuits, cannot be used directly as they need to be converted to layered circuits first
General Circuit vs Layered Circuit
When discussing circuits in the GKR protocol, we refer to layered circuits as arithmetic circuits with gates of two inputs (fan-in 2) from the layer above. In contrast, general circuits have gates that can take inputs from any layers above.
General circuits can be converted into layered circuits simply by adding relay gates in the layers between any two connected gates in nonconsecutive layers. These relay gates simply forward the signals to the next level.
Before Virgo++, the fastest GKR-based protocol was Libra3, which has a prover time linear to the circuit size (i.e. ) for layered circuits. Is there a way to apply the GKR protocol to general circuits also in ?
Yes, of course, this is what we will be discussing next.
Generalizing the GKR protocol
To accept general circuits, the GKR protocol needs two main changes in the underlying sum-check protocol. Let’s examine each one.
Notation: Layers above and below
Throughout this blog post, we refer to the layers as being above the layer , and layers as being below. Looking at the diagram, this may seem counterintuitive at first. However, you must realize that the diagram itself is also upside down because the layer is at the top and the layer is at the bottom.
We use this convention because it is consistent with the research papers that we have reviewed.
Problem #1: Considering Too Many Unused Connections
In GKR, the sum-check equation at each layer is only connected to outputs from the gates in the layer directly above because the circuits are layered. However, for general circuits, as each layer can take inputs from any layers above, the sum-check equation at each layer will have to consider the gates of every layer above.
For each layer , there are summation terms of and from layer to to represent the connections between layer to . This is Equation 4 in the Virgo++ paper.
In Equation 1, the equation considers the gates on a per-layer basis, rather than examining whether each gate is actually connected. When running the GKR protocol on the above equation, the prover needs to send to the verifier evaluations of at random points after running the sum-check protocol at each layer. The resulting prover time is . This is equivalent to converting a general circuit into a layered circuit by adding relay gates, as mentioned earlier. Surely there must be a better way.
Consider Only What Is Needed
In the circuits provided to the GKR protocol, each gate receives output from only two gates above. Thus, there should only be a maximum of 2 times the number of gates in the current layer to be considered for any layer above. We refer to these sets of gates connecting the layers above to the current layer as subsets. Thus, if we can adjust Equation 1 to only consider the subsets of gates from each of the layers above, we should have a much simpler equation. This is the idea behind our adjustments to Equation 1.
Here is the adjusted equation, which is Equation 6 in the paper:
Comparing Equation 2 to Equation 1, we can see that , which refers to all the gates at layer , has been replaced with . refers to only the gates that connect between layer and . The same definition changes apply for , and .
By considering only the used gates for each layer, the size of is now instead of like before. We will see later on how this helps us with improving the prover time to .
Eliminating the Inner Sums
In Equation 2, for each layer it involves a grand sum over many inner sums that include the and predicates for each subset of gates between layer and the layers above. To simplify this equation for efficient execution during the sum-check protocol, we need to reduce it to a single sum.
Currently, each of the inner sums has different bit lengths depending on the number of gates in the subset. To remove the inner sums, we will select the longest binary string in the circuit, denoted as , and force all inner sums to run over it.
Ensuring Shorter Polynomials Are Summed Only Once
When all the inner sums are run over the same binary string, the binary strings that have shorter lengths may be summed multiple times because of the extra padding. To ensure they are only summed over once, we can multiply each of the predicates by the binary string .
Final Sum-Check Equation For Layer
Taking into account of the above 2 points, we are ready to adjust Equation 2 by removing the inner sums and adding the binary string as below (which is Equation 7 in the paper):
Example
Here is an example to illustrate the above two ideas:
Layer | Gates Feeding | Padded Size | Bit-length |
---|---|---|---|
4 gate () | 4 | ||
1 gate () | 2 | ||
4 | 1 gate () | 2 |
The above circuit will give us 3 inner sums:
where represent the outputs of the and gates in the subset for the layer .
Since the longest binary string is from layer 2 with 4 gates, we will set as .
The above 3 subsets will give us 3 inner sums run over the same binary string of :
For each of the sums, we will multiply by the appropriate binary string to ensure it doesn’t get summed over multiple times.
Layer | Bit-length | Binary String to Add | Summation Occurs | Summation Avoided |
---|---|---|---|---|
2 | 2 | none | - | - |
3 | 1 | , which gives: | , which gives: | |
4 | 1 | , which gives: | , which gives: |
This equation of a grand sum over the Boolean hypercube is equivalent to the 3 separate sums in Equation 4.
Problem #2: Combining claims efficiently
Remember that in the original GKR protocol, the verifier uses the sum-check protocol to check that the following equation is computed correctly:
where is a random vector, and are random values in .
When the sum-check protocol for the layer is finished, the verifier needs to compute . To do this, the verifier computes and , and ask the prover to send and . Thus, a claim about the output value, in layer , is reduced to two claims and in layer . The sum-check protocol would repeat on each of the two claims until the claims are reduced to the input layers. You can see that this increases the number of sum-check protocols exponentially with the number of layers.
But recall that we can use a random linear combination to combine the two claims:
where are random values.
The prover and verifier can then execute the sum-check protocol on the random linear combination of claims once and receive claims about the next layer.
Cannot Combine Claims From the New Equation
When we generalize GKR to general circuits, we obtain a new equation (Equation 3) to run the sum-check protocol on. Recall that this equation sums subsets of gates from all the layers above that are connected to the current layer. This means that when the sum-check protocol is finished, we will be left with multiple evaluations of different multilinear extensions defined by subsets from different layers. This invalidates the random linear combination method we previously used, and we must find an alternative method to efficiently combine these evaluation claims.
Sum-check Protocol To The Rescue
As it turns out, the best way to combine these evaluations is through a (yet another) sum-check protocol on an equation that uses a random linear combination. The following is Equation 10 from the paper. Let’s break it down and see how it works.
where are random values chosen by the verifier for each layer .
In the first line of Equation 5, we can see that there is a summation of a random linear combination of two evaluations, one from the subsets of layers below , and two from layer .
To combine the evaluations, we introduce a new function that equals 1 only if the gate in the subset is the same as gate in layer . Since we are dealing with multilinear extensions, we want , which only equals 1 if in the subset is the same gate as from layer . This function helps to rewrite the equation only in terms of as seen in line 2 of Equation 5.
By further rearranging lines 2 to 3 and 4, we obtain an expression, , that only depends on the circuit structure and can be computed by the verifier given .
Now that we have Equation 5, we can use the same linear-time sum-check algorithm used earlier for each layer of our modified GKR protocol (Equation 3).
Linear-time Sum-check Algorithm (To Be Complete)
Let’s review what we have so far:
- To reduce the complexity of the layer equation, we introduce subsets and rewrite Equation 1 into Equation 2 and finally into Equation 3 to be computed using the sum-check protocol.
- To combine the claims efficiently, we introduce Equation 5, which is also intended for the sum-check protocol.
Given the importance of the sum-check protocol, it is only fitting that we have an efficient algorithm to run it.
The sum-check protocol used in the original GKR paper has a prover time of , which is far from ideal. Luckily, we have a better algorithm. Originally introduced in the Libra paper3, the sum-check algorithm there has a prover time of . Thus, applying this efficient sum-check algorithm on our two equations will also give us a linear prover time. While the explanation of this algorithm is out of scope for this post, readers can refer to the paper for a full understanding of how it works.
Conclusion
What makes Virgo++ particularly elegant is how it solves the general circuit problem without fundamentally changing the GKR protocol’s structure. By recognizing that most gates in upper layers are irrelevant to any given gate below, and by using the sum-check protocol not just for the main computation but also for combining claims, the authors achieve something that seemed inherently quadratic in just time. The protocol maintains the same security guarantees as the original GKR while being dramatically more efficient. For practitioners, this means you can now apply GKR directly to your existing circuit representations without worrying about the dd d-factor blowup from adding relay gates—a game-changer for verifiable computation in practice.
Reference
Footnotes
-
Delegating Computation: Interactive Proofs for Muggles by Goldwasser et al. (2008) ↩
-
Doubly Efficient Interactive Proofs for General Arithmetic Circuits with Linear Prover Time (a.k.a. Virgo++) by Zhang et al., (2021) ↩
-
Libra: Succinct Zero-Knowledge Proofs with Optimal Prover Computation by Xie et al. (2019) ↩ ↩2