// Copyright 2021 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

// Code generated by generate.go. DO NOT EDIT.

package fiat

import (
	"crypto/subtle"
	"errors"
)

// P224Element is an integer modulo 2^224 - 2^96 + 1.
//
// The zero value is a valid zero element.
type P224Element struct {
	// Values are represented internally always in the Montgomery domain, and
	// converted in Bytes and SetBytes.
	x p224MontgomeryDomainFieldElement
}

const p224ElementLen = 28

type p224UntypedFieldElement = [4]uint64

// One sets e = 1, and returns e.
func (e *P224Element) One() *P224Element {
	p224SetOne(&e.x)
	return e
}

// Equal returns 1 if e == t, and zero otherwise.
func (e *P224Element) Equal(t *P224Element) int {
	eBytes := e.Bytes()
	tBytes := t.Bytes()
	return subtle.ConstantTimeCompare(eBytes, tBytes)
}

var p224ZeroEncoding = new(P224Element).Bytes()

// IsZero returns 1 if e == 0, and zero otherwise.
func (e *P224Element) IsZero() int {
	eBytes := e.Bytes()
	return subtle.ConstantTimeCompare(eBytes, p224ZeroEncoding)
}

// Set sets e = t, and returns e.
func (e *P224Element) Set(t *P224Element) *P224Element {
	e.x = t.x
	return e
}

// Bytes returns the 28-byte big-endian encoding of e.
func (e *P224Element) Bytes() []byte {
	// This function is outlined to make the allocations inline in the caller
	// rather than happen on the heap.
	var out [p224ElementLen]byte
	return e.bytes(&out)
}

func (e *P224Element) bytes(out *[p224ElementLen]byte) []byte {
	var tmp p224NonMontgomeryDomainFieldElement
	p224FromMontgomery(&tmp, &e.x)
	p224ToBytes(out, (*p224UntypedFieldElement)(&tmp))
	p224InvertEndianness(out[:])
	return out[:]
}

// p224MinusOneEncoding is the encoding of -1 mod p, so p - 1, the
// highest canonical encoding. It is used by SetBytes to check for non-canonical
// encodings such as p + k, 2p + k, etc.
var p224MinusOneEncoding = new(P224Element).Sub(
	new(P224Element), new(P224Element).One()).Bytes()

// SetBytes sets e = v, where v is a big-endian 28-byte encoding, and returns e.
// If v is not 28 bytes or it encodes a value higher than 2^224 - 2^96 + 1,
// SetBytes returns nil and an error, and e is unchanged.
func (e *P224Element) SetBytes(v []byte) (*P224Element, error) {
	if len(v) != p224ElementLen {
		return nil, errors.New("invalid P224Element encoding")
	}
	for i := range v {
		if v[i] < p224MinusOneEncoding[i] {
			break
		}
		if v[i] > p224MinusOneEncoding[i] {
			return nil, errors.New("invalid P224Element encoding")
		}
	}
	var in [p224ElementLen]byte
	copy(in[:], v)
	p224InvertEndianness(in[:])
	var tmp p224NonMontgomeryDomainFieldElement
	p224FromBytes((*p224UntypedFieldElement)(&tmp), &in)
	p224ToMontgomery(&e.x, &tmp)
	return e, nil
}

// Add sets e = t1 + t2, and returns e.
func (e *P224Element) Add(t1, t2 *P224Element) *P224Element {
	p224Add(&e.x, &t1.x, &t2.x)
	return e
}

// Sub sets e = t1 - t2, and returns e.
func (e *P224Element) Sub(t1, t2 *P224Element) *P224Element {
	p224Sub(&e.x, &t1.x, &t2.x)
	return e
}

// Mul sets e = t1 * t2, and returns e.
func (e *P224Element) Mul(t1, t2 *P224Element) *P224Element {
	p224Mul(&e.x, &t1.x, &t2.x)
	return e
}

// Square sets e = t * t, and returns e.
func (e *P224Element) Square(t *P224Element) *P224Element {
	p224Square(&e.x, &t.x)
	return e
}

// Select sets v to a if cond == 1, and to b if cond == 0.
func (v *P224Element) Select(a, b *P224Element, cond int) *P224Element {
	p224Selectznz((*p224UntypedFieldElement)(&v.x), p224Uint1(cond),
		(*p224UntypedFieldElement)(&b.x), (*p224UntypedFieldElement)(&a.x))
	return v
}

func p224InvertEndianness(v []byte) {
	for i := 0; i < len(v)/2; i++ {
		v[i], v[len(v)-1-i] = v[len(v)-1-i], v[i]
	}
}
