---
name: "libpll"
section: "3"
platform: "linux"
package: "libpll-dev"
version: "0.3.2-5+b1"
release: "Debian 13 (Trixie)"
platforms: ["linux"]
url: "https://new.carta.tech/libpll"
---

# libpll(3)

Phylogenetic Likelihood Library

## NAME

libpll — Phylogenetic Likelihood Library

## SYNOPSIS

Partition management

**pll\_partition\_t \* pll\_partition\_create(unsigned int** *tips***, unsigned int** *clv\_buffers***, unsigned int** *states***, unsigned int** *sites***, unsigned int** *rate\_matrices***, unsigned int** *prob\_matrices***, unsigned int** *rate\_cats***, unsigned int** *scale\_buffers***, unsigned int** *attributes***);**

**void pll\_partition\_destroy(pll\_partition\_t \*** *partition***);**

Partition parameters setup

**int pll\_set\_tip\_states(pll\_partition\_t \*** *partition***, unsigned int** *tip\_index***, const unsigned int \*** *map***, const char \*** *sequence***);**

**int pll\_set\_tip\_clv(pll\_partition\_t \*** *partition***, unsigned int** *tip\_index***, const double \*** *clv***);**

**void pll\_set\_pattern\_weights(pll\_partition\_t \*** *partition***, const unsigned int \*** *pattern\_weights***);**

**int pll\_set\_asc\_bias\_type(pll\_partition\_t \*** *partition***, int** *asc\_bias\_type***);**

**void pll\_set\_asc\_state\_weights(pll\_partition\_t \*** *partition***, const unsigned int \*** *state\_weights***);**

**void pll\_set\_subst\_params(pll\_partition\_t \*** *partition***, unsigned int** *params\_index***, const double \*** *params***);**

**void pll\_set\_frequencies(pll\_partition\_t \*** *partition***,  unsigned int** *params\_index***, const double \*** *frequencies***);**

**void pll\_set\_category\_rates(pll\_partition\_t \*** *partition***, const double \*** *rates***);**

**void pll\_set\_category\_weights(pll\_partition\_t \*** *partition***, const double \*** *rate\_weights***);**

Transition probability matrices

**int pll\_update\_prob\_matrices(pll\_partition\_t \*** *partition***, const unsigned int \*** *params\_index***, const unsigned int \*** *matrix\_indices***, const double \*** *branch\_lengths***, unsigned int** *count***);**

**int pll\_update\_eigen(pll\_partition\_t \*** *partition***, unsigned int** *params\_index***);**

**void pll\_show\_pmatrix(pll\_partition\_t \*** *partition***, unsigned int** *index***, unsigned int** *float\_precision***);**

Invariant sites

**unsigned int pll\_count\_invariant\_sites(pll\_partition\_t \*** *partition***, unsigned int \*** *state\_inv\_count***);**

**int pll\_update\_invariant\_sites(pll\_partition\_t \*** *partition***);**

**int pll\_update\_invariant\_sites\_proportion(pll\_partition\_t \*** *partition***, unsigned int** *params\_index***, double** *prop\_invar***);**

Conditional probability vectors

**void pll\_update\_partials(pll\_partition\_t \*** *partition***, const pll\_operation\_t \*** *operations***, unsigned int** *count***);**

**void pll\_show\_clv(pll\_partition\_t \*** *partition***, unsigned int** *clv\_index***, int** *scaler\_index***, unsigned int** *float\_precision***);**

Evaluation of log-Likelihood

**double pll\_compute\_root\_loglikelihood(pll\_partition\_t \*** *partition***, unsigned int** *clv\_index***, int** *scaler\_index***, const unsigned int \*** *freqs\_index***, double \*** *persite\_lnl***);**

**double pll\_compute\_edge\_loglikelihood(pll\_partition\_t \*** *partition***, unsigned int** *parent\_clv\_index***, int** *parent\_scaler\_index***, unsigned int** *child\_clv\_index***, int** *child\_scaler\_index***, unsigned int** *matrix\_index***, const unsigned int \*** *freqs\_index***, double \*** *persite\_lnl***);**

Likelihood function derivatives

**int pll\_update\_sumtable(pll\_partition\_t \*** *partition***, unsigned int** *parent\_clv\_index***, unsigned int** *child\_clv\_index***, const unsigned int \*** *params\_indices***, double \*** *sumtable***);**

**int pll\_compute\_likelihood\_derivatives(pll\_partition\_t \*** *partition***, int** *parent\_scaler\_index***, int** *child\_scaler\_index***, double** *branch\_length***, const unsigned int \*** *params\_indices***, const double \*** *sumtable***, double \*** *d\_f***, double \*** *dd\_f***);**

FASTA file handling

**pll\_fasta\_t \* pll\_fasta\_open(const char \*** *filename***, const unsigned int \*** *map***);**

**int pll\_fasta\_getnext(pll\_fasta\_t \*** *fd***, char \*\*** *head***, long \*** *head\_len***, char \*\*** *seq***, long \*** *seq\_len***, long \*** *seqno***);**

**void pll\_fasta\_close(pll\_fasta\_t \*** *fd***);**

**long pll\_fasta\_getfilesize(pll\_fasta\_t \*** *fd***);**

**long pll\_fasta\_getfilepos(pll\_fasta\_t \*** *fd***);**

**int pll\_fasta\_rewind(pll\_fasta\_t \*** *fd***);**

PHYLIP file handling

**pll\_msa\_t \* pll\_phylip\_parse\_msa(const char \*** *filename***, unsigned int \*** *msa\_count***);**

**void pll\_msa\_destroy(pll\_msa\_t \*** *msa***);**

Newick handling

**pll\_rtree\_t \* pll\_rtree\_parse\_newick(const char \*** *filename***, unsigned int \*** *tip\_count***);**

**pll\_utree\_t \* pll\_utree\_parse\_newick(const char \*** *filename***, unsigned int \*** *tip\_count***);**

**pll\_utree\_t \* pll\_utree\_parse\_newick\_string(char \*** *s***, unsigned int \*** *tip\_count***);**

Unrooted tree structure manipulation

**void pll\_utree\_destroy(pll\_utree\_t \*** *root***);**

**void pll\_utree\_show\_ascii(pll\_utree\_t \*** *tree***, int** *options***);**

**char \* pll\_utree\_export\_newick(pll\_utree\_t \*** *root***);**

**int pll\_utree\_traverse(pll\_utree\_t \*** *root***, int (\****cbtrav***)(pll\_utree\_t \*), pll\_utree\_t \*\*** *outbuffer***, unsigned int \*** *trav\_size***);**

**unsigned int pll\_utree\_query\_tipnodes(pll\_utree\_t \*** *root***, pll\_utree\_t \*\*** *node\_list***);**

**unsigned int pll\_utree\_query\_innernodes(pll\_utree\_t \*** *root***, pll\_utree\_t \*\*** *node\_list***);**

**void pll\_utree\_create\_operations(pll\_utree\_t \*\*** *trav\_buffer***, unsigned int** *trav\_buffer\_size***, double \*** *branches***, unsigned int \*** *pmatrix\_indices***, pll\_operation\_t \*** *ops***, unsigned int \*** *matrix\_count***, unsigned int \*** *ops\_count***);**

**int pll\_utree\_check\_integrity(pll\_utree\_t \*** *root***);**

**pll\_utree\_t \* pll\_utree\_clone(pll\_utree\_t \*** *root***);**

**pll\_utree\_t \* pll\_rtree\_unroot(pll\_rtree\_t \*** *root***);**

**int pll\_utree\_every(pll\_utree\_t \*** *node***, int (\****cb***)(pll\_utree\_t \*));**

Rooted tree structure manipulation

**void pll\_rtree\_destroy(pll\_rtree\_t \*** *root***);**

**void pll\_rtree\_show\_ascii(pll\_rtree\_t \*** *tree***, int** *options***);**

**char \* pll\_rtree\_export\_newick(pll\_rtree\_t \*** *root***);**

**int pll\_rtree\_traverse(pll\_rtree\_t \*** *root***, int (\****cbtrav***)(pll\_rtree\_t \*), pll\_rtree\_t \*\*** *outbuffer***, unsigned int \*** *trav\_size***);**

**unsigned int pll\_rtree\_query\_tipnodes(pll\_rtree\_t \*** *root***, pll\_rtree\_t \*\*** *node\_list***);**

**unsigned int pll\_rtree\_query\_innernodes(pll\_rtree\_t \*** *root***, pll\_rtree\_t \*\*** *node\_list***);**

**void pll\_rtree\_create\_operations(pll\_rtree\_t \*\*** *trav\_buffer***, unsigned int** *trav\_buffer\_size***, double \*** *branches***, unsigned int \*** *pmatrix\_indices***, pll\_operation\_t \*** *ops***, unsigned int \*** *matrix\_count***, unsigned int \*** *ops\_count***);**

**void pll\_rtree\_create\_pars\_buildops(pll\_rtree\_t \*\*** *trav\_buffer***, unsigned int** *trav\_buffer\_size***, pll\_pars\_buildop\_t \*** *ops***, unsigned int \*** *ops\_count***);**

**void pll\_rtree\_create\_pars\_recops(pll\_rtree\_t \*\*** *trav\_buffer***, unsigned int** *trav\_buffer\_size***, pll\_pars\_recop\_t \*** *ops***, unsigned int \*** *ops\_count***);**

Topological rearrangement moves

**int pll\_utree\_spr(pll\_utree\_t \*** *p***, pll\_utree\_t \*** *r***, pll\_utree\_rb\_t \*** *rb***, double \*** *branch\_lengths***, unsigned int \*** *matrix\_indices***);**

**int pll\_utree\_spr\_safe(pll\_utree\_t \*** *p***, pll\_utree\_t \*** *r***, pll\_utree\_rb\_t \*** *rb***, double \*** *branch\_lengths***, unsigned int \*** *matrix\_indices***);**

**int pll\_utree\_nni(pll\_utree\_t \*** *p***, int** *type***, pll\_utree\_rb\_t \*** *rb***);**

**int pll\_utree\_rollback(pll\_utree\_rb\_t \*** *rollback***, double \*** *branch\_lengths***, unsigned int \*** *matrix\_indices***);**

Parsimony functions

**int pll\_set\_parsimony\_sequence(pll\_parsimony\_t \*** *pars***, unsigned int** *tip\_index***, const unsigned int \*** *map***, const char \*** *sequence***);**

**pll\_parsimony\_t \* pll\_parsimony\_create(unsigned int \*** *tips***, unsigned int** *states***, unsigned int** *sites***, double \*** *score\_matrix***, unsigned int** *score\_buffers***, unsigned int** *ancestral\_buffers***);**

**double pll\_parsimony\_build(pll\_parsimony\_t \*** *pars***, pll\_pars\_buildop\_t \*** *operations***, unsigned int** *count***);**

**void pll\_parsimony\_reconstruct(pll\_parsimony\_t \*** *pars***, const unsigned int \*** *map***, pll\_pars\_recop\_t \*** *operations***, unsigned int** *count***);**

**double pll\_parsimony\_score(pll\_parsimony\_t \*** *pars***, unsigned int** *score\_buffer\_index***);**

**void pll\_parsimony\_destroy(pll\_parsimony\_t \*** *pars***);**

Auxiliary functions

**int pll\_compute\_gamma\_cats(double** *alpha***, unsigned int** *categories***, double \*** *output\_rates***);**

**void \* pll\_aligned\_alloc(size\_t** *size***, size\_t** *alignment***);**

**void pll\_aligned\_free(void \*** *ptr***);**

**unsigned int \* pll\_compress\_site\_patterns(char \*\*** *sequence***, const unsigned int \*** *map***, int** *count***, int \*** *length***);**

Core functions

**void pll\_core\_create\_lookup(unsigned int** *states***, unsigned int** *rate\_cats***, double \*** *lookup***, const double \*** *left\_matrix***, const double \*** *right\_matrix***, unsigned int \*** *tipmap***, unsigned int** *tipmap\_size***, unsigned int** *attrib***);**

**void pll\_core\_update\_partial\_tt(unsigned int** *states***, unsigned int** *sites***, unsigned int** *rate\_cats***, double \*** *parent\_clv***, unsigned int \*** *parent\_scaler***, const unsigned char \*** *left\_tipchars***, const unsigned char \*** *right\_tipchars***, const unsigned int \*** *tipmap***, unsigned int** *tipmap\_size***, const double \*** *lookup***, unsigned int** *attrib***);**

**void pll\_core\_update\_partial\_ti(unsigned int** *states***, unsigned int** *sites***, unsigned int** *rate\_cats***, double \*** *parent\_clv***, unsigned int \*** *parent\_scaler***, const unsigned char \*** *left\_tipchars***, const double \*** *right\_clv***, const double \*** *left\_matrix***, const double \*** *right\_matrix***, const unsigned int \*** *right\_scaler***, const unsigned int \*** *tipmap***, unsigned int** *attrib***);**

**void pll\_core\_update\_partial\_ii(unsigned int** *states***, unsigned int** *sites***, unsigned int** *rate\_cats***, double \*** *parent\_clv***, unsigned int \*** *parent\_scaler***, const double \*** *left\_clv***, const double \*** *right\_clv***, const double \*** *left\_matrix***, const double \*** *right\_matrix***, const unsigned int \*** *left\_scaler***, const unsigned int \*** *right\_scaler***, unsigned int** *attrib***);**

**int pll\_core\_update\_sumtable\_ti(unsigned int** *states***, unsigned int** *sites***, unsigned int** *rate\_cats***, const double \*** *parent\_clv***, const unsigned char \*** *left\_tipchars***, double \*\*** *eigenvecs***, double \*\*** *inv\_eigenvecs***, double \*\*** *freqs***, unsigned int \*** *tipmap***, double \*** *sumtable***, unsigned int** *attrib***);**

**int pll\_core\_likelihood\_derivatives(unsigned int** *states***, unsigned int***sites***, unsigned int** *rate\_cats***, const double \*** *rate\_weights***, const unsigned int \*** *parent\_scaler***, const unsigned int \*** *child\_scaler***, const int \*** *invariant***, const unsigned int \*** *pattern\_weights***, double** *branch\_length***, const double \*** *prop\_invar***, double \*\*** *freqs***, const double \*** *rates***, double \*\*** *eigenvals***, const double \*** *sumtable***, double  \*** *d\_f***, double \*** *dd\_f***, unsigned int** *attrib***);**

**double pll\_core\_edge\_loglikelihood\_ii(unsigned int** *states***, unsigned int** *sites***, unsigned int** *rate\_cats***, const double \*** *parent\_clv***, const unsigned int \*** *parent\_scaler***, const double \*** *child\_clv***, const unsigned int \*** *child\_scaler***, const double \*** *pmatrix***, double \*\*** *frequencies***, const double \*** *rate\_weights***, const unsigned int \*** *pattern\_weights***, const double \*** *invar\_proportion***, const int \*** *invar\_indices***, const unsigned int \*** *freqs\_indices***, double \*** *persite\_lnl***, unsigned int** *attrib***);**

**double pll\_core\_edge\_loglikelihood\_ti(unsigned int** *states***, unsigned int** *sites***, unsigned int** *rate\_cats***, const double \*** *parent\_clv***, const unsigned int \*** *parent\_scaler***, const unsigned char \*** *tipchars***, const unsigned int \*** *tipmap***, const double \*** *pmatrix***, double \*\*** *frequencies***, const double \*** *rate\_weights***, const unsigned int \*** *pattern\_weights***, const double \*** *invar\_proportion***, const int \*** *invar\_indices***, const unsigned int \*** *freqs\_indices***, double \*** *persite\_lnl***, unsigned int** *attrib***);**

**int pll\_core\_update\_pmatrix(double \*** *pmatrix***, unsigned int** *states***, double** *rate***, double** *prop\_invar***, double** *branch\_length***, double \*** *eigenvals***, double \*** *eigenvecs***, double \*** *inv\_eigenvecs***, unsigned int** *attrib***);**

## DESCRIPTION

**libpll** is a library for phylogenetics.

- **pll\_partition\_t \* pll\_partition\_create(unsigned int** *tips***, unsigned int** *clv\_buffers***, unsigned int** *states***, unsigned int** *sites***, unsigned int** *rate\_matrices***, unsigned int** *prob\_matrices***, unsigned int** *rate\_cats***, unsigned int** *scale\_buffers***, unsigned int** *attributes***);**

  Creates a partition with either *tips* character arrays or *tips* CLV arrays (depending on *attributes*, see **Partition Attributes**), and, additionally, *clv\_buffers* CLV vectors, for storing conditional probabilities at inner nodes.  The partition structure is constructed for *states* number of states (e.g. 4 for nucleotide and 20 for amino-acid data) and sufficient space is allocated to host an alignment of size *sites*\**tips*. The number of rate matrices that can be used is given by *rate\_matrices*. Additionally, the function allocates space for hosting *rate\_matrices* arrays of substitution parameters, frequencies, and auxiliary eigen-decomposition arrays (transparent to the user). The parameter *prob\_matrices* dictates the number of probability matrices for which space will be allocated. This parameter is typically set to the number of branches the tree has (e.g., 2n-3 for unrooted and 2n-2 for rooted, where n is the number of tips/leaves). libpll will automatically create space for *prob\_matrices*\**rate\_cats*, where *rate\_cats* is the number of different rate categories. The array of probability matrices is indexed from 0 to *prob\_matrices*-1. Each matrix entry consists of sufficient space to accommodate *rate\_cats* matrices, which are stored consecutively in memory. Note that libpll will not allocate space for the different substitution matrices specified by *rate\_matrices*. The user must indicate that to libpll by multiplying *prob\_matrices* with the corresponding factor. Finally, *scale\_buffers* sets the number of scaling buffers to be allocated, and attributes states the hardware acceleration options to be used (see **Partition Attributes**). The function returns a pointer to the allocated **pll\_partition\_t** structure. Note that, *rate\_matrices* are used to address heterotachy, i.e. transition probability matrices computed from different rate matrices. For more information, see **Updating transition** **probability matrices**.

- **void pll\_partition\_destroy(pll\_partition\_t \*** *partition***);**

  Deallocates all data associated with the partition pointed by *partition*.

- **int pll\_set\_tip\_states(pll\_partition\_t \*** *partition***, unsigned int** *tip\_index***, const unsigned int \*** *map***, const char \*** *sequence***);**

  Set the tip CLV (or tip character array) with index *tip\_index* of instance partition, according to the character sequence *sequence* and the conversion table *map*, which translates (or maps) characters to states. For an example see **Setting CLV vectors at tips from sequences and maps**.

- **int pll\_set\_tip\_clv(pll\_partition\_t \*** *partition***, unsigned int** *tip\_index***, const double \*** *clv***);**

  Set the tip CLV with index *tip\_index* of instance *partition*, to the contents of the array *clv*. For an example see **Setting CLV vectors** **manually**. Note, this function cannot be used in conjunction with the **PLL\_ATTRIB\_PATTERN\_TIP** (see **Partition Attributes**).

- **void pll\_set\_subst\_params(pll\_partition\_t \*** *partition***, unsigned int** *params\_index***, const double \*** *params***);**

  Sets the parameters for substitution model with index *params\_index*, where *params\_index* ranges from 0 to *rate\_matrices*-1, as specified in the **pll\_partition\_create()** call. Array *params* should contain exactly (*states*\**states*-*states*)/2 parameters of type **double**. These values correspond to the upper triangle elements (above the main diagonal) of the rate matrix.

- **void pll\_set\_frequencies(pll\_partition\_t \*** *partition***, unsigned int** *params\_index***, const double \*** *frequencies***);**

  Sets the base frequencies for the substitution model with index *params\_index*, where *params\_index* ranges from 0 to *rate\_matrices*-1, as specified in the **pll\_partition\_create()** call. The array of base frequencies (frequencies) is copied into the instance. The order of bases in the array depends on the encoding used when converting tip sequences to CLV. For example, if the **pll\_map\_nt** map was used with the **pll\_set\_tip\_states()** function to describe nucleotide data, then the order is A, C, G, T. However, this can be arbitrarily set by adjusting the provided map.

- **void pll\_set\_pattern\_weights(pll\_partition\_t \*** *partition***, const unsigned int \*** *pattern\_weights***);**

  Sets the vector of pattern weights (*pattern\_weights*) for partition. The function reads and copies the first *partition*-\>sites elements of *pattern\_weights* into *partition*-\>pattern\_weights.

- **void pll\_set\_category\_rates(pll\_partition\_t \*** *partition***, const double \*** *rates***);**

  Sets the rate categories for *partition*. The function reads and copies the first *partition*-\>rate\_cats elements of array rates into *partition*-\>rates.

- **int pll\_update\_invariant\_sites(pll\_partition\_t \*** *partition***);**

  Updates the invariant sites array *partition*-\>invariant, according to the sequences in the partition. This function is implicitly called by **pll\_update\_invariant\_sites\_proportion()** when the specified proportion of invariant sites is greater than zero, but it must be explicitly called by the client code if the sequences change.

- **int pll\_update\_invariant\_sites\_proportion(pll\_partition\_t \*** *partition***, unsigned int** *params\_index***, double** *prop\_invar***);**

  Updates the proportion of invariant sites for the *partition* rate matrix with with index *params\_index*. Note that, this call will not implicitly update the transition probability matrices computed from the particular rate matrix, but must be done explicitly for example with a call to **pll\_update\_prob\_matrices()**.

- **int pll\_update\_prob\_matrices(pll\_partition\_t \*** *partition***, const unsigned int \*** *params\_index***, const unsigned int \*** *matrix\_indices***, const double \*** *branch\_lengths***, unsigned int** *count***);**

  Computes the transition probability matrices specified by the *count* indices in *matrix\_indices*, for all rate categories. A matrix with index *matrix\_indices*\[i\] will be computed using the branch length *branch\_lengths*\[i\]. To compute the matrix for rate category j, the function uses the rate matrix with index *params\_indices*\[j\]. Matrices are stored in *partition*-\>pmatrix\[*matrix\_indices*\[i\]\]. Note that, each such entry holds the matrices for all rate categories, stored consecutively in memory.

- **int pll\_update\_eigen(pll\_partition\_t \*** *partition***, unsigned int** *params\_index***);**

  Updates the eigenvectors (*partition*-\>eigenvecs\[*params\_index*\]), inverse eigenvectors (*partition*-\>eigenvecs\[*params\_index*\]), and eigenvalues (*partition*-\>eigenvals\[*params\_index*\]) using the substitution parameters (*partition*-\>subst\_params\[*params\_index*\]) and base frequencies (*partition*-\>frequencies\[*params\_index*\]) specified by *params\_index*.

- **void pll\_show\_pmatrix(pll\_partition\_t \*** *partition***, unsigned int** *index***, unsigned int** *float\_precision***);**

  Prints the transition probability matrices for each rate category of *partition* associated with *index* to standard output. The floating point precision is dictated by *float\_precision*.

- **unsigned int pll\_count\_invariant\_sites(pll\_partition\_t \*** *partition***, unsigned int \*** *state\_inv\_count***);**

  Returns the number of invariant sites in the sequence alignment from *partition*.  The array *state\_inv\_count* must be of size *partition*-\>states and is filled such that entry i contains the count of invariant sites for state i.

- **int pll\_update\_invariant\_sites(pll\_partition\_t \*** *partition***);**

  Updates the invariant sites array *partition*-\>invariant, according to the sequences in the partition. This function is implicitly called by **pll\_update\_invariant\_sites\_proportion()** when the specified proportion of invariant sites is greater than zero, but it must be explicitly called by the client code if the sequences change.

- **int pll\_update\_invariant\_sites\_proportion(pll\_partition\_t \*** *partition***, unsigned int** *params\_index***, double** *prop\_invar***);**

  Updates the proportion of invariant sites for the rate matrix of *partition* with index *params\_index*. Note that, this call will not implicitly update the transition probability matrices computed from the particular rate matrix, but must be done explicitly for example with a call to **pll\_update\_prob\_matrices()**.

- **void pll\_update\_partials(pll\_partition\_t \*** *partition***, const pll\_operation\_t \*** *operations***, unsigned int** *count***);**

  Updates the *count* conditional probability vectors (CPV) defined by the entries of *operations*, in the order they appear in the array. Each *operations* entry describes one CPV from *partition*. See also **pll\_operation\_t**.

- **void pll\_show\_clv(pll\_partition\_t \*** *partition***, unsigned int** *clv\_index***, int** *scaler\_index***, unsigned int** *float\_precision***);**

  Prints to standard output the conditional probability vector for index *clv\_index* from *partition*, using the scale buffer with index *scaler\_index*.  If no scale buffer was used, then *scaler\_index* must be passed the value **PLL\_SCALE\_BUFFER\_NONE**. The floating precision (number of digits after decimal point) is dictated by *float\_precision*. The output contains brackets, curly braces and round brackets to separate the values as sites, rate categories and states related, respectively.

- **double pll\_compute\_root\_loglikelihood(pll\_partition\_t \*** *partition***, unsigned int** *clv\_index***, int** *scaler\_index***, const unsigned int \*** *freqs\_index***, double \*** *persite\_lnl***);**

  Evaluates the log-likelihood of a rooted tree, for the vector of conditional probabilities (partials) with index *clv\_index*, scale buffer with index *scaler\_index* (or **PLL\_SCALE\_BUFFER\_NONE**), and base frequencies arrays with indices *freqs\_index* (one per rate category). If *persite\_lnl* is not **NULL**, then it must be large enough to hold *partition*-\>sites double-precision values, and will be filled with the per-site log-likelihoods.

- **double pll\_compute\_edge\_loglikelihood(pll\_partition\_t \*** *partition***, unsigned int** *parent\_clv\_index***, int** *parent\_scaler\_index***, unsigned int** *child\_clv\_index***, int** *child\_scaler\_index***, unsigned int** *matrix\_index***, const unsigned int \*** *freqs\_index***, double \*** *persite\_lnl***);**

  Evaluates the log-likelihood of an unrooted tree, by providing the conditional probability vectors (partials) for two nodes that share an edge  with indices *parent\_clv\_index* resp. *child\_clv\_index*, scale buffers with indices *parent\_scaler\_index* resp. *child\_clv\_index* (or **PLL\_SCALE\_BUFFER\_NONE**), the transition probability matrix with index *matrix\_index* and base frequencies arrays with indices *freqs\_index* (one per rate category). If *persite\_lnl* is not **NULL**, then it must be large enough to hold *partition*\>sites\` double-precision values, and will be filled with the per-site log-likelihoods.

## AVAILABILITY

Source code and binaries are available at \<https://github.com/xflouris/libpll\>.

## COPYRIGHT

Copyright (C) 2015-2017, Tomas Flouri, Diego Darriba

All rights reserved.

Contact: Tomas Flouri \<Tomas.Flouri@h-its.org\>, Scientific Computing, Heidelberg Insititute for Theoretical Studies, 69118 Heidelberg, Germany

This software is licensed under the terms of the GNU Affero General Public License version 3.

**GNU Affero General Public License version 3**

This program is free software: you can redistribute it and/or modify it under the terms of the GNU Affero General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.

This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Affero General Public License for more details.

You should have received a copy of the GNU Affero General Public License along with this program.  If not, see \<http://www.gnu.org/licenses/\>.

## VERSION HISTORY

New features and important modifications of **libpll** (short lived or minor bug releases may not be mentioned):

- **v0.2.0** released September 9th, 2016

  First public release.

- **v0.3.0** released May 15th, 2017

  Added faster vectorizations for 20-state and arbitrary-state models, unweighted parsimony functions, randomized stepwise addition, portable functions for parsing trees from C-strings, per-rate category scalers for preventing numerical underflows. Modified newick exporting function to accept callbacks for custom printing. Fixed derivatives computation, parsing of branch lengths, invariant sites computation, log-likelihood computation for cases where we have scaling and patterns, ascertainment bias computation, per-site log-likelihood computation, memory leaks. Added run-time detection of hardware.

- **v0.3.1** released May 17th, 2017

  Correct updating of paddded eigen-decomposition arrays for models with a number of states not being a power of two. Added portable hardware detection for clang and GCC.

- **v0.3.2** released July 12th, 2017

  Added optional per-rate category scalers for protein and generic kernels. Improved fix for negative transition probability matrices caused by numerics. Fixed initialization of tip CLVs when using ascertainment bias correction with non-DNA sequences. Fixed excessive memory allocation when compressing site patterns and issue with PHYLIP parsing when header ends with CRLF.
