# Security Threat Model

## Asset Definition & Scope

-   **Component:** EPPlus (.NET Open XML Spreadsheet Library, AppSheet fork)
-   **Repository:** Git-on-Borg
    (`https://gnocchi-internal.googlesource.com/third_party/epplus`, branch
    `main`)
-   **Scope:** Shared .NET library providing server-side reading, parsing,
    generation, manipulation, and formula evaluation of Microsoft Excel OpenXML
    (`.xlsx`, `.xlsm`) spreadsheets within AppSheet backend services.

## Prioritization Signals

-   **1P OSS:** No (Third-party open-source library maintained as an internal
    customized fork for Google AppSheet)
-   **1P Proprietary Shipped Software:** No (Server-side shared library bundled
    into AppSheet backend services)
-   **High-Risk Code Surface:** Yes (Complex file format parsing including ZIP
    archive extraction, XML document/stream deserialization, XPath queries, cell
    store indexing, and formula lexical analysis/expression evaluation)
-   **Perimeter Exposure:** Yes (Indirectly exposed to the public Internet via
    AppSheet application endpoints processing end-user and customer spreadsheet
    uploads)
-   **Data Sensitivity:** High (Parses and generates customer spreadsheet data
    containing confidential business data, PII, financial figures, and
    application schemas)
-   **Untrusted Input Handling:** Yes (Processes untrusted Excel files,
    compressed ZIP archives, XML parts, cell definitions, formatting rules, and
    user-supplied formulas)
-   **Business Value:** Core dependency for AppSheet's spreadsheet integration
    and data source connectors; security defects (XXE, Zip Slip, formula
    injection, or DoS) could lead to service disruption, customer data exposure,
    or server compromise.

## Scanning Harness Prompts

-   Focus on XML External Entity (XXE) and XML Entity Expansion (Billion Laughs
    / XML bomb) vulnerabilities across all `XmlDocument`, `XmlReader`, and
    `XPath` operations (e.g., verify that `XmlReaderSettings.ProhibitDtd = true`
    / `DtdProcessing.Prohibit` and `XmlResolver = null` are strictly enforced
    across `XmlHelper.cs`, `ZipPackage.cs`, `ExcelStyles.cs`,
    `ExcelWorksheets.cs`, and table/drawing components).
-   Focus on archive extraction safety in `ZipPackage.cs` (`ZipArchive`
    handling) for Zip Slip path traversal vulnerabilities (e.g., handling
    malformed entry full names or URI paths containing `../`), uncompressed size
    limits, and zip bomb resource exhaustion.
-   Focus on the formula parsing and execution engine
    (`FormulaParsing/FormulaParser.cs`, `ExpressionGraph`, `LexicalAnalysis`)
    for recursive stack overflow, unhandled exceptions, denial-of-service via
    circular references, or unintended method invocation.
-   Focus on memory exhaustion, integer overflows, or unchecked allocations in
    `CellStore.cs` when processing large row/column indices or sparse matrices
    crafted to cause OutOfMemory errors.
-   Focus on CSV / formula injection risks when writing cell contents or
    formatting export outputs.

## Entry Points and Untrusted Inputs

Entry Point                                                  | Type                         | Trusted? | Validation
------------------------------------------------------------ | ---------------------------- | -------- | ----------
`ExcelPackage(Stream)` / `ExcelPackage(FileInfo)`            | API Constructor / File Input | No       | Validates stream existence; delegates archive decompression to `ZipPackage`
`ZipPackage(Stream)`                                         | Archive Decompressor         | No       | Checks for `[content_types].xml` and relationship parts; reads entry streams into byte arrays
`XmlHelper.LoadXmlSafe(XmlDocument, Stream)`                 | XML Deserialization          | No       | Configures `XmlReaderSettings.ProhibitDtd = true` before loading into `XmlDocument`
`FormulaParser.Parse(string)` / `ExcelRangeBase.Calculate()` | Formula Engine               | No       | Lexical tokenization and expression graph evaluation of formula strings
`ExcelWorksheet.Cells[...]` / `CellStore`                    | Data Ingestion               | No       | Range address parsing, dimension bounding, and cell value type mapping

## Trust Boundaries and Auth Assumptions

-   **Authentication**: None at library level. Authentication is assumed to be
    handled upstream by AppSheet API gateways and services before passing
    document streams.
-   **Authorization**: None at library level. Access control to spreadsheet data
    is enforced by AppSheet application authorization layers.
-   **Implicit trust**: The library assumes memory allocations and execution
    timeouts are constrained by the host process container/sandbox, but must
    guard against internal crashes or excessive resource consumption.
-   **Boundary crossings**: Public customer uploads $\rightarrow$ AppSheet
    service frontend $\rightarrow$ AppSheet backend worker $\rightarrow$ EPPlus
    parsing engine $\rightarrow$ AppSheet in-memory data structures.

## Sensitive Data Paths

| Data Type       | Source           | Destination        | Protection         |
| --------------- | ---------------- | ------------------ | ------------------ |
| Customer        | External File    | AppSheet Memory /  | In-memory          |
: Spreadsheet     : Upload / Data    : `CellStore`        : processing;        :
: Content         : Source           :                    : protected by host  :
:                 :                  :                    : sandbox and TLS    :
:                 :                  :                    : transport          :
| Spreadsheet     | Excel File Parts | Formula Parsing    | Evaluated in       |
: Formulas &      :                  : Engine             : memory; restricted :
: Macros          :                  :                    : to supported       :
:                 :                  :                    : spreadsheet        :
:                 :                  :                    : function library   :
| Office Document | OpenXML          | `OfficeProperties` | Parsed into        |
: Metadata        : Properties       : object             : strongly-typed     :
:                 :                  :                    : metadata           :
:                 :                  :                    : properties         :

## Privileged Actions

| Action              | Location                | Guard                      |
| ------------------- | ----------------------- | -------------------------- |
| File Read / Stream  | `ExcelPackage.Load` /   | Validates stream integrity |
: Ingestion           : `ZipPackage.ZipPackage` :                            :
| File Write /        | `ExcelPackage.Save` /   | File system permissions of |
: Serialization       : `ExcelPackage.SaveAs`   : running process            :
| XML Deserialization | `XmlHelper.LoadXmlSafe` | DTD prohibition settings   |

## Priority Review Areas

1.  **XML Parser Hardening**: Verify all XML loading routines across the library
    consistently use safe `XmlReader` settings prohibiting DTD processing and
    external entity resolution.
2.  **Zip Slip & Path Traversal**: Review `ZipPackage.cs` part URI parsing and
    relationship mapping (`ReadRelation`) to ensure no arbitrary path escapes
    occur during package part extraction.
3.  **Formula Engine Resilience**: Audit `FormulaParsing` components for
    recursive evaluation depth limits, CPU consumption attacks, and safe
    handling of malformed formulas.
4.  **Memory Allocation Limits**: Inspect `CellStore.cs` and worksheet data
    structures for defensive memory allocation bounds when handling massive or
    maliciously sparse spreadsheets.
