PyREC scaffolding (from YREC development, 7be4133)/ surfp.fGlossary

surfp.f

155 lines · 1 definitions · on GitHub (7be4133)

Python version: surfp.py, 146 lines, on the right (switch to Python above the code).

Variables on this page (14)

ap, at, atmgl, atmpl, atmtl, imin, iminmax, iowr, ishort, istor, jp, kp, ng, nt

Purpose

SURFP gives the pressure at $T = T_\mathrm{eff}$ in a model atmosphere, by interpolating a table of $\log P$ in $\log T_\mathrm{eff}$ and $\log g$. It is the outer boundary of the envelope integration with Kurucz atmospheres (KTTAU = 3). With KTTAU = 4 SETUPS reads the same table, but SURFP is not called: a run with Allard atmospheres that leaves their table falls back to the gray atmosphere, not to this one (atmos2_mod.f, question 1).

How it fits

  • Inputs: $\log T_\mathrm{eff}$ (TEFFL) and $\log g$ (GL); the table in ATMOS2_MOD (ATMPL(57,11), the grids ATMTL, ATMGL), read by SETUPS; and in FAC_MOD, the lowest and highest valid gravity index for each temperature (IMIN, IMINMAX), also set by SETUPS.
  • Who calls it: ENVINT, for KTTAU = 3. Its siblings are KCSURFP (Kurucz–Castelli tables, KTTAU = 5) and ALSURFP (Allard tables, KTTAU = 4).
  • What it calls: INTER3 (3-point Lagrange weights), KSPLINE and KSPLINT (a natural cubic spline through four points).
  • Outputs: in ATMPRT_MOD, AP = $\log P$ and AT = $\log T_\mathrm{eff}$, read by ENVINT (and QATM, MASSLOSS); JP and KP in FAC_MOD, the table cell used. With LPRT, a line on ISHORT and ISTOR (units from IOUNITS_MOD).

The method

  1. Stop the run if $\log T_\mathrm{eff} < 3.5$ or $\log g < -0.5$, with exit status 1.

  2. Find four table temperatures around $T_\mathrm{eff}$.

  3. At each of them, interpolate $\log P$ in $\log g$: for $\log T > 4.55$ linearly between the two highest gravities; for $4.5 < \log T \le 4.55$ with the 3-point Lagrange formula on the three highest gravities; otherwise with a natural cubic spline through the four valid gravities nearest $\log g$ (the top four, a bracketing four, or the bottom four).

  4. Interpolate the four values in $\log T_\mathrm{eff}$ with a natural cubic spline through four points.

The four-point spline, for points $x_1 < \dots < x_4$, is the cubic-spline formula of splint.f with natural ends.

The header (lines 38–41↗) describes an older method: It says the routine interpolates "USING A 4-POINT LAGRANGIAN INTERPOLATOR" and "WILL QUIT IF THE DESIRED DATA POINT HAS TEFF OR LOG G MORE THAN ONE TABLE POINT FROM THE DATA," but the code uses 4-point splines (the Lagrange calls INTRP2 are commented out), except for table rows with $\log T_\mathrm{eff} > 4.5$, where gravity is interpolated linearly (above 4.55, lines 71–75↗) or with the 3-point Lagrange INTER3 (lines 77–82↗), and it checks only the lower limits of $T_\mathrm{eff}$ and $g$ (line 44↗).

Suspected bugs, checked by running the code

Each bug is marked by what running the code showed: (changes results, large) or (small), the fix moving a run clearly beyond a null change; (stops the run); (wrong output), the fix changing only what is written; (harmless in the runs), within the noise; (never occurred), the code ran but the fault did not; (not reached); (cannot be reached), a guard prevents it; (withdrawn), the suspicion was wrong.

1. (never occurred) Missing gravities used at the top of a row.

(lines 88–102↗; lines 104–123↗) SETUPS sets IMINMAX(J), the highest gravity with a pressure, below NG when a temperature's highest-gravity entries are $-999$ (setups.f, lines 270–299↗). G. Somers limited the general case's search to IMINMAX(J) "to prevent using -999," but the top-four branch (GL.GE.ATMGL(NG-1)) still takes the gravities NG-3 … NG, and KK = MIN(NG-3,KK) still allows them. The general search covers $\log g$ only up to ATMGL(IMINMAX(J)-1). In such a row, a $\log g$ from there up to ATMGL(NG-1) = 4.5 matches no interval and falls through to the lowest four valid gravities, a long extrapolation; a $\log g \ge 4.5$ takes the top four, $-999$ entries included, into the spline. The tables in input/atmos/kurucz/ with $[\mathrm{Fe/H}] \le -2.3$ (atmk1990m23.tab to atmk1990m50.tab) have such rows at $\log T_\mathrm{eff}$ = 3.53–3.68 (for example atmk1990m40.tab: no pressure above $\log g$ = 3.0 at 3.544), where cool dwarfs have $\log g \approx 4.5$–5; the other Kurucz 1990 tables have none below $\log T$ = 4.5, apart from an empty row at 4.041 in atmk1990p01.tab, above the switch to gray at 3.95. What follows: a wrong surface pressure AP for a cool metal-poor dwarf. Only with KTTAU = 3 (the default is 0, gray) and one of these tables.

A possible fix:

surfp.f

@@ lines 85–95 @@
             ENDIF
             GOTO 20
          ENDIF
-         IF(GL.GE.ATMGL(NG-1))THEN
+C 11/09/26 KC via Claude
+C code changed to use IMINMAX(J), the highest gravity with a pressure,
+C in place of NG, so that missing (-999) values at the top of a row
+C are not used, and the general search reaches the top of the row.
+         IF(GL.GE.ATMGL(IMINMAX(J)-1))THEN
 C DESIRED LOG G ABOVE SECOND TO TOP TABLE LOG G - USE TOP 4 LOG G VALUES.
             DO KK = 1,4
-               QG(KK)=ATMGL(NG-4+KK)
-               PTAB(KK) = ATMPL(J,NG-4+KK)
+               QG(KK)=ATMGL(IMINMAX(J)-4+KK)
+               PTAB(KK) = ATMPL(J,IMINMAX(J)-4+KK)
             END DO
 C            CALL INTRP2(QR,QG,GL)
             CALL KSPLINE(QG,PTAB,YG)
@@ lines 97–103 @@
 C            PP(N) = ATMPL(J,NG-3)*QG(1)+ATMPL(J,NG-2)*QG(2)+
 C     *              ATMPL(J,NG-1)*QG(3)+ATMPL(J,NG)*QG(4)
             PP(N) = Y0
-            KP(N) = NG-3
+            KP(N) = IMINMAX(J)-3
             GOTO 20
          ENDIF
 C GENERAL CASE - FIND 4 NEAREST POINTS IN GRAVITY THAT ARE IN THE TABLE.
@@ lines 106–112 @@
          DO K = IMINMAX(J)-3,IMIN(J),-1
             IF(GL.LT.ATMGL(K+2).AND.GL.GE.ATMGL(K+1))THEN
                KK = MAX(IMIN(J),K)
-               KK = MIN(NG-3,KK)
+               KK = MIN(IMINMAX(J)-3,KK)
                DO KKK = 1,4
                   QG(KKK) = ATMGL(KK+KKK-1)
                   PTAB(KKK) = ATMPL(J,KK+KKK-1)

Checked by running YREC (Nov 9, 2026; a line added at each suspected path counted how often it was taken, the outputs otherwise unchanged): The branch ran in the two runs of 34 runs (26 of YREC's cases, from a 0.04 $M_\odot$ brown dwarf and the solar models to 9 $M_\odot$, rotation, and helium burning, and 8 made-up ones; one of these, with FCORE = 1.0, stopped in its first second) with KTTAU = 3, testsuite/Test_solarGS98_kurucz (10,264 times) and testsuite/Test_solarM22M_difkur (14,236 times), both with atmk1990p00.tab, at $\log T_\mathrm{eff}$ = 3.63 to 3.76 and $\log g$ = 2.70 to 4.57; no row with missing highest gravities was met, as expected for that table. A cool dwarf with one of the metal-poor tables ($[\mathrm{Fe/H}] \le -2.3$) would reach it; none was run. No fix was run. Intent: The comment (lines 104–105↗) says the change to IMINMAX was made "to prevent using -999"; only the loop's start was changed.

Definitions

subroutineSURFP

lines 1–155 · GitHub

$\log P$ at $T = T_\mathrm{eff}$ from the Kurucz atmosphere table, by interpolation in $\log g$ then $\log T_\mathrm{eff}$.

Uses modules ATMOS2_MOD, ATMPRT_MOD, FAC_MOD, IOUNITS_MOD

Called by ENVINT

Flowchart of its calls, in order (9)
for J = JJ,JJ+3 (DO 20), lines 66–138
if (ATMTL(J).GT.4.5D0), lines 70–87
if (GL.GE.ATMGL(NG-1)), lines 88–102
for K = IMINMAX(J)-3,IMIN(J),-1, lines 106–123
if (GL.LT.ATMGL(K+2).AND.GL.GE.ATMGL(K+1)), lines 107–122

Change log

The changes since rp_1

Changed since rp_1. Declarations only: COMMON blocks to modules (/ATMOS2/, /FAC/, /ATMPRT/ and /LUOUT/ to ATMOS2_MOD, FAC_MOD, ATMPRT_MOD and IOUNITS_MOD; the unused parameters NTC, NGC dropped), IMPLICIT NONE.

Changed since a8a5950. The out-of-table stop ends the run with exit status 1 (STOP 1) instead of a bare STOP, which exited with 0 (KNOWN_ISSUES.md, issue 38).