Beispiel #1
0
void tex::show_glue(ptr p)
	{
	if (tex::subtype(p) >= A_LEADERS) {
		show_leaders(p);
	} else {
		print_esc("glue");
		if (tex::subtype(p) != NORMAL)
			show_glue_type(tex::subtype(p));
		if (tex::subtype(p) != COND_MATH_GLUE) {
			print(" ");
			if (tex::subtype(p) < COND_MATH_GLUE)
				print_spec(glue_ptr(p), null_str);
			else print_spec(glue_ptr(p), "mu");
		}
	}
}
Beispiel #2
0
tex::glue_t::glue_t(glue_t *q)
	{
	tex::type(this) = GLUE_NODE;
	tex::subtype(this) = NORMAL;
	leader_ptr(this) = 0;
	glue_ptr(this) = q;
	incr(glue_ref_count(q));
	}
Beispiel #3
0
void tex::show_leaders(ptr p)
	{
	print_esc(null_str);
	if (tex::subtype(p) == C_LEADERS)
		print("c");
	else if (tex::subtype(p) == X_LEADERS)
		print("x");
	print("leaders ");
	print_spec(glue_ptr(p), null_str);
	node_list_display(leader_ptr(p));
}
Beispiel #4
0
ptr tex::prune_page_top(ptr p)
	{
	mcell	m;
	ptr	prev_p;
	ptr	q, s, t;

	t = (ptr)&m;
	prev_p = t;
	link(t) = p;
	while (p != null) {
		switch (type(p))
		{
		case HLIST_NODE:
		case VLIST_NODE:
		case RULE_NODE:
			q = new_skip_param(SPLIT_TOP_SKIP_CODE);
			link(prev_p) = q;
			link(q) = p;
			s = glue_ptr(q);
			if (glue_width(s) > box_height(p)) {
				glue_width(s) -= box_height(p);
			} else {
				glue_width(s) = 0;
			}
			p = null;
			break;

		case WHATSIT_NODE:
		case MARK_NODE:
		case INS_NODE:
			prev_p = p;
			p = link(p);
			break;
		
		case GLUE_NODE:
		case KERN_NODE:
		case PENALTY_NODE:
			q = p;
			p = link(p);
			link(q) = null;
			link(prev_p) = p;
			flush_node_list(q);
			break;

		default:
			confusion("pruning");
			break;
		}
	}
	return (link(t));
}
Beispiel #5
0
void tex::append_to_vlist(ptr b)
	{
	scal	d;
	ptr	p;

	append_to_vlist_called=true;
	if (prev_depth > IGNORE_DEPTH) {
		d = glue_width(baseline_skip) - prev_depth - box_height(b);
		if (d < line_skip_limit) {
			p = new_param_glue(LINE_SKIP_CODE);
			} 
		else {
			p = new_skip_param(BASELINE_SKIP_CODE);
			glue_width(glue_ptr(p)) = d;
			}
		tail_append(p);
		}
	tail_append(b);
	prev_depth = box_depth(b);
	}
Beispiel #6
0
void pdf_vlist_out (void)
{
  scaled left_edge;
  scaled top_edge;
  scaled save_h, save_v;
  pointer this_box;
  // glue_ord g_order;
  int g_order;
  // char g_sign;
  int g_sign;
  pointer p;
  integer save_loc;
  pointer leader_box;
  scaled leader_ht;
  scaled lx;
  boolean outer_doing_leaders;
  scaled edge;
  real glue_temp;
  real cur_glue;
  scaled cur_g;

  cur_g = 0;
  cur_glue = 0.0;
  this_box = temp_ptr;
  g_order = glue_order(this_box);
  g_sign = glue_sign(this_box);
  p = list_ptr(this_box);
  incr(cur_s);

  if (cur_s > max_push)
    max_push = cur_s;

  save_loc = dvi_offset + dvi_ptr;
  left_edge = cur_h;
  cur_v = cur_v - height(this_box);
  top_edge = cur_v;

  while (p != 0)
  {
    if (is_char_node(p))
    {
      confusion("vlistout");
      return;
    }
    else
    {
      switch (type(p))
      {
        case hlist_node:
        case vlist_node:
          if (list_ptr(p) == 0)
            cur_v = cur_v + height(p) + depth(p);
          else
          {
            cur_v = cur_v + height(p);
            pdf_synch_v();
            save_h = dvi_h;
            save_v = dvi_v;
            cur_h = left_edge + shift_amount(p);
            temp_ptr = p;

            if (type(p) == vlist_node)
              pdf_vlist_out();
            else
              pdf_hlist_out();

            dvi_h = save_h;
            dvi_v = save_v;
            cur_v = save_v + depth(p);
            cur_h = left_edge;
          }
          break;

        case rule_node:
          {
            rule_ht = height(p);
            rule_dp = depth(p);
            rule_wd = width(p);
            goto fin_rule;
          }
          break;

        case whatsit_node:
          out_what(p);
          break;

        case glue_node:
          {
            g = glue_ptr(p);
            rule_ht = width(g) - cur_g;

            if (g_sign != normal)
            {
              if (g_sign == stretching)
              {
                if (stretch_order(g) == g_order)
                {
                  cur_glue = cur_glue + stretch(g);
                  vet_glue(glue_set(this_box) * cur_glue);
                  cur_g = round(glue_temp);
                }
              }
              else if (shrink_order(g) == g_order)   /* BUG FIX !!! */
              {
                cur_glue = cur_glue - shrink(g);
                vet_glue(glue_set(this_box) * cur_glue);
                cur_g = round(glue_temp);
              }
            }

            rule_ht = rule_ht + cur_g;

            if (subtype(p) >= a_leaders)
            {
              leader_box = leader_ptr(p);

              if (type(leader_box) == rule_node)
              {
                rule_wd = width(leader_box);
                rule_dp = 0;
                goto fin_rule;
              }

              leader_ht = height(leader_box) + depth(leader_box);

              if ((leader_ht > 0) && (rule_ht > 0))
              {
                rule_ht = rule_ht + 10;
                edge = cur_v + rule_ht;
                lx = 0;

                if (subtype(p) == a_leaders)
                {
                  save_v = cur_v;
                  cur_v = top_edge + leader_ht * ((cur_v - top_edge) / leader_ht);

                  if (cur_v < save_v)
                    cur_v = cur_v + leader_ht;
                }
                else
                {
                  lq = rule_ht / leader_ht;
                  lr = rule_ht % leader_ht;

                  if (subtype(p) == c_leaders)
                    cur_v = cur_v + (lr / 2);
                  else
                  {
                    lx = (2 * lr + lq + 1) / (2 * lq + 2);
                    cur_v = cur_v + ((lr - (lq - 1) * lx) / 2);
                  }
                }

                while (cur_v + leader_ht <= edge)
                {
                  cur_h = left_edge + shift_amount(leader_box);
                  pdf_synch_h();
                  save_h = dvi_h;
                  cur_v = cur_v + height(leader_box);
                  pdf_synch_v();
                  save_v = dvi_v;
                  temp_ptr = leader_box;
                  outer_doing_leaders = doing_leaders;
                  doing_leaders = true;

                  if (type(leader_box) == vlist_node)
                    pdf_vlist_out();
                  else
                    pdf_hlist_out();

                  doing_leaders = outer_doing_leaders;
                  dvi_v = save_v;
                  dvi_h = save_h;
                  cur_h = left_edge;
                  cur_v = save_v - height(leader_box) + leader_ht + lx;
                }

                cur_v = edge - 10;
                goto next_p;
              }
            }

            goto move_past;
          }
          break;

        case kern_node:
          cur_v = cur_v + width(p);
          break;

        default:
          break;
      }

      goto next_p;

fin_rule:
      if (is_running(rule_wd))
        rule_wd = width(this_box);

      rule_ht = rule_ht + rule_dp;
      cur_v = cur_v + rule_ht;

      if ((rule_ht > 0) && (rule_wd > 0))
      {
        pdf_synch_h();
        pdf_synch_v();
        pdf_dev_set_rule(dvi_h, -dvi_v, rule_wd, rule_ht);
      }

      goto next_p;

move_past:
      cur_v = cur_v + rule_ht;
    }

next_p:
    p = link(p);
  }

  prune_movements(save_loc);
  decr(cur_s);
}
Beispiel #7
0
void pdf_hlist_out (void)
{
  scaled base_line;
  scaled left_edge;
  scaled save_h, save_v;
  pointer this_box;
  // glue_ord g_order;
  int g_order;
  // char g_sign;
  int g_sign;
  pointer p;
  integer save_loc;
  pointer leader_box;
  scaled leader_wd;
  scaled lx;
  boolean outer_doing_leaders;
  scaled edge;
  real glue_temp;
  real cur_glue;
  scaled cur_g;

  cur_g = 0;
  cur_glue = 0.0;
  this_box = temp_ptr;
  g_order = glue_order(this_box);
  g_sign = glue_sign(this_box);
  p = list_ptr(this_box);
  incr(cur_s);

  if (cur_s > max_push)
    max_push = cur_s;

  save_loc = dvi_offset + dvi_ptr;
  base_line = cur_v;
  left_edge = cur_h;

  while (p != 0)
reswitch:
  if (is_char_node(p))
  {
    pdf_synch_h();
    pdf_synch_v();

    do
    {
      f = font(p);
      c = character(p);

      if (f != dvi_f)
      {
        if (!font_used[f])
        {
          font_used[f] = true;
          font_id[f]   = pdf_get_font_id(f);
        }

        dvi_f = f;
      }

      pdf_out_char(dvi_f, c);
      cur_h = cur_h + char_width(f, char_info(f, c));
      p = link(p);
    } while (!(!is_char_node(p)));

    dvi_h = cur_h;
  }
  else
  {
    switch (type(p))
    {
      case hlist_node:
      case vlist_node:
        if (list_ptr(p) == 0)
          cur_h = cur_h + width(p);
        else
        {
          save_h = dvi_h;
          save_v = dvi_v;
          cur_v = base_line + shift_amount(p);
          temp_ptr = p;
          edge = cur_h;

          if (type(p) == vlist_node)
            pdf_vlist_out();
          else
            pdf_hlist_out();

          dvi_h = save_h;
          dvi_v = save_v;
          cur_h = edge + width(p);
          cur_v = base_line;
        }
        break;

      case rule_node:
        {
          rule_ht = height(p);
          rule_dp = depth(p);
          rule_wd = width(p);
          goto fin_rule;
        }
        break;

      case whatsit_node:
        out_what(p);
        break;

      case glue_node:
        {
          g = glue_ptr(p);
          rule_wd = width(g) - cur_g;

          if (g_sign != normal)
          {
            if (g_sign == stretching)
            {
              if (stretch_order(g) == g_order)
              {
                cur_glue = cur_glue + stretch(g);
                vet_glue(glue_set(this_box) * cur_glue);
                cur_g = round(glue_temp);
              }
            }
            else if (shrink_order(g) == g_order)
            {
              cur_glue = cur_glue - shrink(g);
              vet_glue(glue_set(this_box) * cur_glue);
              cur_g = round(glue_temp);
            }
          }

          rule_wd = rule_wd + cur_g;

          if (subtype(p) >= a_leaders)
          {
            leader_box = leader_ptr(p);

            if (type(leader_box) == rule_node)
            {
              rule_ht = height(leader_box);
              rule_dp = depth(leader_box);
              goto fin_rule;
            }

            leader_wd = width(leader_box);

            if ((leader_wd > 0) && (rule_wd > 0))
            {
              rule_wd = rule_wd + 10;
              edge = cur_h + rule_wd;
              lx = 0;

              if (subtype(p) == a_leaders)
              {
                save_h = cur_h;
                cur_h = left_edge + leader_wd * ((cur_h - left_edge) / leader_wd);

                if (cur_h < save_h)
                  cur_h = cur_h + leader_wd;
              }
              else
              {
                lq = rule_wd / leader_wd;
                lr = rule_wd % leader_wd;

                if (subtype(p) == c_leaders)
                  cur_h = cur_h + (lr / 2);
                else
                {
                  lx = (2 * lr + lq + 1) / (2 * lq + 2);
                  cur_h = cur_h + ((lr - (lq - 1)* lx) / 2);
                }
              }

              while (cur_h + leader_wd <= edge)
              {
                cur_v = base_line + shift_amount(leader_box);
                pdf_synch_v();
                save_v = dvi_v;
                pdf_synch_h();
                save_h = dvi_h;
                temp_ptr = leader_box;
                outer_doing_leaders = doing_leaders;
                doing_leaders = true;

                if (type(leader_box) == vlist_node)
                  pdf_vlist_out();
                else
                  pdf_hlist_out();

                doing_leaders = outer_doing_leaders;
                dvi_v = save_v;
                dvi_h = save_h;
                cur_v = base_line;
                cur_h = save_h + leader_wd + lx;
              }

              cur_h = edge - 10;
              goto next_p;
            }
          }

          goto move_past;
        }
        break;

      case kern_node:
      case math_node:
        cur_h = cur_h + width(p);
        break;

      case ligature_node:
        {
          mem[lig_trick] = mem[lig_char(p)];
          link(lig_trick) = link(p);
          p = lig_trick;
          goto reswitch;
        }
        break;

      default:
        break;
    }

    goto next_p;

fin_rule:
    if (is_running(rule_ht))
      rule_ht = height(this_box);

    if (is_running(rule_dp))
      rule_dp = depth(this_box);

    rule_ht = rule_ht + rule_dp;

    if ((rule_ht > 0) && (rule_wd > 0))
    {
      pdf_synch_h();
      cur_v = base_line + rule_dp;
      pdf_synch_v();
      pdf_dev_set_rule(dvi_h, -dvi_v, rule_wd, rule_ht);
      cur_v = base_line;
      dvi_h = dvi_h + rule_wd;
    }

move_past:
    cur_h = cur_h + rule_wd;

next_p:
    p = link(p);
  }

  prune_movements(save_loc);
  decr(cur_s);
}
Beispiel #8
0
void tex::build_page ()
	{
	int	pi=0, b, c;
	ptr	p, q, r;
	
#define INF_SHRINK_PAGE "Infinite glue shrinkage found on current page"
	
	if (link(contrib_head) == null || output_active)
		return;
	do {
		p = link(contrib_head);
		if (last_glue != null)
			delete_glue_ref(last_glue);
		last_penalty = 0;
		last_kern = 0;
		if (type(p) == GLUE_NODE) {
			last_glue = glue_ptr(p);
			add_glue_ref(last_glue);
		} else {
			last_glue = null;
			if (type(p) == PENALTY_NODE) {
				last_penalty = penalty(p);
			} else if (type(p) == KERN_NODE) {
				last_kern = kern_width(p);
			}
		}
		switch (type(p))
		{
		case HLIST_NODE:
		case VLIST_NODE:
		case RULE_NODE:
			if (page_contents < BOX_THERE) {
				if (page_contents == EMPTY) {
					freeze_page_specs(BOX_THERE);
				} else {
					page_contents = BOX_THERE;
				}
				q = new_skip_param(TOP_SKIP_CODE);
				link(q) = p;
				link(contrib_head) = q;
				r = glue_ptr(q);
				if (glue_width(r) > box_height(p)) {
					glue_width(r) -= box_height(p);
				} else {
					glue_width(r) = 0;
				}
				continue;
			} else {
				page_total += page_depth + box_height(p);
				page_depth = box_depth(p);
				goto contribute;
			}
		
		case GLUE_NODE:
			if (page_contents < BOX_THERE) {
				goto done;
			} else if (precedes_break(page_tail)) {
				pi = 0;
			} else {
				goto update_heights;
			}
			break;
		
		case KERN_NODE:
			if (page_contents < BOX_THERE) {
				goto done;
			} else if (link(p) == null) {
				return;
			} else if (type(link(p)) == GLUE_NODE) {
				pi = 0;
			} else {
				goto update_heights;
			}
			break;
		
		case PENALTY_NODE:
			if (page_contents < BOX_THERE) {
				goto done;
			} else {
				pi = penalty(p);
			}
			break;

		case WHATSIT_NODE:
			goto contribute;
		
		case MARK_NODE:
			goto contribute;

		case INS_NODE:
			insert_page(p);
			goto contribute;
		
		default:
			confusion("page");
			break;
		}
		if (pi < INF_PENALTY) {
			b = page_badness();
			if (b < AWFUL_BAD) {
				if (pi <= EJECT_PENALTY) {
					c = pi;
				} else if (b < INF_BAD) {
					c = b + pi + insert_penalties;
				} else {
					c = DEPLORABLE;
				}
			} else {
				c = b;
			}
			if (insert_penalties >= 10000)
				c = AWFUL_BAD;
			if (tracing_pages > 0)
				show_page_stats(b, pi, c);
			if (c <= least_page_cost) {
				best_page_break = p;
				best_size = page_goal;
				least_page_cost = c;
				r = link(page_ins_head);
				while (r != page_ins_head) {
					best_ins_ptr(r) = last_ins_ptr(r);
					r = link(r);
				}
			}
			if (c == AWFUL_BAD || pi <= EJECT_PENALTY) {
				fire_up(p);
				if (output_active)
					return;
				continue;
			}
		}
		if (type(p) < GLUE_NODE || type(p) > KERN_NODE) {
			goto contribute;
		}
		
	update_heights:
		if (type(p) == KERN_NODE) {
			page_total += page_depth + kern_width(p);
		} else {
			q = glue_ptr(p);
			page_so_far[2 + stretch_order(q)] += stretch(q);
			page_shrink += shrink(q);
			if (shrink_order(q) != NORMAL && shrink(q) != 0) {
				print_err(INF_SHRINK_PAGE);
				help_inf_shrink_page();
				error();
				r = new_spec(q);
				shrink_order(r) = NORMAL;
				delete_glue_ref(q);
				q = glue_ptr(p) = r;
			}
			page_total += page_depth + glue_width(q);
		}
		page_depth = 0;

	contribute:
		if (page_depth > page_max_depth) {
			page_total = page_total + page_depth - page_max_depth;
			page_depth = page_max_depth;
		}
		page_tail = link(page_tail) = p;
		link(contrib_head) = link(p);
		link(p) = null;
		continue;

	done:
		link(contrib_head) = link(p);
		link(p) = null;
		flush_node_list(p);
	} while (link(contrib_head) != null);
	if (nest_ptr == nest) {
		tail = contrib_head;
	} else {
		contrib_tail = contrib_head;
	}
}
Beispiel #9
0
ptr tex::vert_break(ptr p, scal h, scal d)
	{
	int	b;
	ptr	q;
	ptr	r;
	int	t;
	int	pi=0;
	ptr	prev_p;
	scal	prev_dp;
	ptr	best_place=0;
	int	least_cost;

#define	INF_SHRINK_BOX "Infinite glue shrinkage found in box being split"

	prev_p = p;
	least_cost = AWFUL_BAD;
	do_all_six(set_height_zero);
	prev_dp = 0;
	loop {
		if (p == null) {
			pi = EJECT_PENALTY;
		} else {
			switch (type(p))
			{
			case HLIST_NODE:
			case VLIST_NODE:
			case RULE_NODE:
				cur_height += prev_dp + box_height(p);
				prev_dp = box_depth(p);
				goto not_found;
			
			case WHATSIT_NODE:
				goto not_found;
			
			case GLUE_NODE:
				if (precedes_break(prev_p)) {
					pi = 0;
				} else {
					goto update_heights;
				}
				break;
			
			case KERN_NODE:
				if (link(p) == null) {
					t = PENALTY_NODE;
				} else {
					t = type(link(p));
				}
				if (t == GLUE_NODE) {
					pi = 0;
				} else {
					goto update_heights;
				}
				break;
			
			case PENALTY_NODE:
				pi = penalty(p);
				break;
			
			case MARK_NODE:
			case INS_NODE:
				goto not_found;
			
			default:
				confusion("vertbreak");
			}
		}
		if (pi < INF_PENALTY) {
			b = vert_badness(h);
			if (b < AWFUL_BAD) {
				if (pi <= EJECT_PENALTY) {
					b = pi;
				} else if (b < INF_BAD) {
					b += pi;
				} else {
					b = DEPLORABLE;
				}
			}
			if (b <= least_cost) {
				best_place = p;
				least_cost = b;
				best_height_plus_depth = cur_height + prev_dp;
			}
			if (b == AWFUL_BAD || pi <= EJECT_PENALTY) {
				return best_place;
			}
		}
		if (type(p) < GLUE_NODE || type(p) > KERN_NODE) {
			goto not_found;
		}

	update_heights:
		if (type(p) == KERN_NODE) {
			cur_height += prev_dp + kern_width(p);
		} else {
			q = glue_ptr(p);
			active_height[2 + stretch_order(q)] += stretch(q);
			active_height[6] += shrink(q);
			if (shrink_order(q) != NORMAL && shrink(q) != 0) {
				print_err(INF_SHRINK_BOX);
				help_inf_shrink_box();
				error();
				r = new_spec(q);
				delete_glue_ref(q);
				shrink_order(r) = NORMAL;
				glue_ptr(p) = r;
			}
			cur_height += prev_dp + glue_width(q);
		}
		prev_dp = 0;

	not_found:
		if (prev_dp > d) {
			cur_height = cur_height + prev_dp - d;
			prev_dp = d;
		}
		prev_p = p;
		p = link(prev_p);
	}
}
Beispiel #10
0
void tex::init_math ()
	{
	fnt	f;
	int	m, n;
	ptr	p, q;
	scal	d, l, s, v, w;

	get_token();
	if (cur_cmd == MATH_SHIFT && mode > 0) {
		if (head == tail) {
			pop_nest();
			w = -MAX_DIMEN;
		} else {
			line_break(display_widow_penalty);
			v = shift_amount(just_box) + 2 * quad(cur_font);
			w = -MAX_DIMEN;
			p = list_ptr(just_box);
			while (p != null) {
		reswitch:
				if (is_char_node(p)) {
					f = font(p);
					d = char_width(f,
						char_info(f, character(p)));
					goto found;
				}
				switch (type(p))
				{
				case HLIST_NODE:
				case VLIST_NODE:
				case RULE_NODE:
					d = box_width(p);
					goto found;
				
				case LIGATURE_NODE:
					p = make_char_from_lig(p);
					goto reswitch;
				
				case KERN_NODE:
					d = kern_width(p);
					break;

				case MATH_NODE:
					d = box_width(p);
					break;

				case GLUE_NODE:
					q = glue_ptr(p);
					d = box_width(q);
					if (glue_sign(just_box) ==
						STRETCHING) {
						if (glue_order(just_box) ==
							stretch_order(q)
						&& stretch(q) != 0)
							v = MAX_DIMEN;
					} else if (glue_sign(just_box) ==
						SHRINKING)  {
						if (glue_order(just_box) ==
							shrink_order(q)
						&& shrink(q) != 0) 
							v = MAX_DIMEN;
					}
					if (subtype(p) >= A_LEADERS)	
						goto found;
					break;

				case WHATSIT_NODE: 
					d = 0;
					break;

				default:
					d = 0;
					break;
				}
				if (v < MAX_DIMEN)
					v += d;
				goto not_found;
			
			found:
				if (v < MAX_DIMEN) {
					v += d;
					w = v;
				} else {
					w = MAX_DIMEN;
					break;
				}

			not_found:
				p = link(p);
			}
		}
		if (par_shape_ptr == null) {
			if (hang_indent != 0
			&& (hang_after >= 0
				&& prev_graf + 2 > hang_after
					|| prev_graf + 1 < -hang_after)) {
				l = hsize - abs(hang_indent);
				s = (hang_indent > 0) ? hang_indent : 0;
			} else {
				l = hsize;
				s = 0;
			}
		} else {
			n = info(par_shape_ptr);
			if (prev_graf + 2 >= n)
				m = n;
			else m = prev_graf + 2;
			l = par_shape_width(m);
			s = par_shape_indent(m);
		}
		push_math(MATH_SHIFT_GROUP);
		mode = MMODE;
		reg_define(int_reg[CUR_FAM_CODE], INT_REG, -1);
		reg_define(dimen_reg[PRE_DISPLAY_SIZE_CODE], DIMEN_REG, w);
		reg_define(dimen_reg[DISPLAY_WIDTH_CODE], DIMEN_REG, l);
		reg_define(dimen_reg[DISPLAY_INDENT_CODE], DIMEN_REG, s);
		if (every_display != null)
			begin_token_list(every_display, EVERY_DISPLAY_TEXT);
		if (nest_ptr == nest + 1)
			build_page();
	} else {
		back_input(); 
		push_math(MATH_SHIFT_GROUP);
		reg_define(int_reg[CUR_FAM_CODE], INT_REG, -1);
		if (every_math != null)
			begin_token_list(every_math, EVERY_MATH_TEXT);
	}
}
Beispiel #11
0
ptr tex::copy_node_list(ptr p)
	{
	ptr	h;
	ptr	q;
	ptr	r=0;

	h = q = new_avail();
	while (p != null) {
		if (is_char_node(p)) {
			r = new_avail();
			font(r) = font(p);
			character(r) = character(p);
		} else {
			switch (type(p))
			{
			case HLIST_NODE:
			case VLIST_NODE:
			case UNSET_NODE:
				r = tex::new_node(BOX_NODE_SIZE);
				memcpy((void *)r, (void *)p, BOX_NODE_SIZE);
				list_ptr(r) = copy_node_list(list_ptr(p));
				break;
			
			case RULE_NODE:
				r = tex::new_node(RULE_NODE_SIZE);
				memcpy((void *)r, (void *)p, RULE_NODE_SIZE);
				break;

			case INS_NODE:
				r = tex::new_node(INS_NODE_SIZE);
				memcpy((void *)r, (void *)p, INS_NODE_SIZE);
				add_glue_ref(split_top_ptr(p));
				ins_ptr(r) = copy_node_list(ins_ptr(p));
				break;

			case WHATSIT_NODE:
				r = copy_whatsit(p);
				break;
			
			case GLUE_NODE:
				r = tex::new_node(SMALL_NODE_SIZE);
				memcpy((void *)r, (void *)p, SMALL_NODE_SIZE);
				add_glue_ref(glue_ptr(p));
				glue_ptr(r) = glue_ptr(p);
				leader_ptr(r) = copy_node_list(leader_ptr(p));
				break;
			
			case KERN_NODE:
			case MATH_NODE:
			case PENALTY_NODE:
				r = tex::new_node(SMALL_NODE_SIZE);
				memcpy((void *)r, (void *)p, SMALL_NODE_SIZE);
				break;
			
			case LIGATURE_NODE:
				r = tex::new_node(SMALL_NODE_SIZE);
				memcpy((void *)r, (void *)p, SMALL_NODE_SIZE);
				lig_ptr(r) = copy_node_list(lig_ptr(p));
				break;
				
			case DISC_NODE:
				r = tex::new_node(SMALL_NODE_SIZE);
				memcpy((void *)r, (void *)p, SMALL_NODE_SIZE);
				pre_break(r) = copy_node_list(pre_break(p));
				post_break(r) = copy_node_list(post_break(p));
				break;

			case MARK_NODE:
				r = tex::new_node(SMALL_NODE_SIZE);
				memcpy((void *)r, (void *)p, SMALL_NODE_SIZE);
				add_token_ref(mark_ptr(p));
				break;

			case ADJUST_NODE:
				r = tex::new_node(SMALL_NODE_SIZE);
				memcpy((void *)r, (void *)p, SMALL_NODE_SIZE);
				adjust_ptr(r) = copy_node_list(adjust_ptr(p));
				break;
			
			default:
				confusion("copying");
				break;
			}
		}
		q = link(q) = r;
		p = link(p);
	}
	link(q) = null;
	q = link(h);
	free_avail(h);
	return q;
}
Beispiel #12
0
void tex::flush_node_list(ptr p)
	{
	ptr	q;

	while (p != null) {
		q = link(p);
		if (is_char_node(p)) {
			free_avail(p);
		} else {
			switch (type(p))
			{
			case HLIST_NODE:
			case VLIST_NODE:
			case UNSET_NODE:
				flush_node_list(list_ptr(p));
				free_node(p, BOX_NODE_SIZE);
				goto done;
					
			case RULE_NODE:
				free_node(p, RULE_NODE_SIZE);
				goto done;

			case INS_NODE:
				flush_node_list(ins_ptr(p));
				delete_glue_ref(split_top_ptr(p));
				free_node(p, INS_NODE_SIZE);
				goto done;

			case WHATSIT_NODE:
				free_whatsit(p);
				goto done;
			
			case GLUE_NODE:
				fast_delete_glue_ref(glue_ptr(p));
				if (leader_ptr(p) != null)
					flush_node_list(leader_ptr(p));
				break;

			case KERN_NODE:
			case MATH_NODE:
			case PENALTY_NODE:
				break;

			case LIGATURE_NODE:
				flush_node_list(lig_ptr(p));
				break;

			case MARK_NODE:
				delete_token_ref(mark_ptr(p));
				break;
			
			case DISC_NODE:
				flush_node_list(pre_break(p));
				flush_node_list(post_break(p));
				break;

			case ADJUST_NODE:
				flush_node_list(adjust_ptr(p));
				break;

			case STYLE_NODE:
				free_node(p, STYLE_NODE_SIZE);
				goto done;

			case CHOICE_NODE:
				flush_node_list(display_mlist(p));
				flush_node_list(text_mlist(p));
				flush_node_list(script_mlist(p));
				flush_node_list(script_script_mlist(p));
				free_node(p, STYLE_NODE_SIZE);
				goto done;

			case ORD_NOAD:
			case OP_NOAD:
			case BIN_NOAD:
			case REL_NOAD:
			case OPEN_NOAD:
			case CLOSE_NOAD:
			case PUNCT_NOAD:
			case INNER_NOAD:
			case RADICAL_NOAD:
			case OVER_NOAD:
			case UNDER_NOAD:
			case VCENTER_NOAD:
			case ACCENT_NOAD:
				if (math_type(nucleus(p)) >= SUB_BOX)
					flush_node_list(math_link(nucleus(p)));
				if (math_type(supscr(p)) >= SUB_BOX)
					flush_node_list(math_link(supscr(p)));
				if (math_type(subscr(p)) >= SUB_BOX)
					flush_node_list(math_link(subscr(p)));
				if (type(p) == RADICAL_NOAD)
					free_node(p, RADICAL_NOAD_SIZE);
				else if (type(p) == ACCENT_NOAD)
					free_node(p, ACCENT_NOAD_SIZE);
				else free_node(p, NOAD_SIZE);
				goto done;
			
			case LEFT_NOAD:
			case RIGHT_NOAD:
				free_node(p, NOAD_SIZE);
				goto done;
			
			case FRACTION_NOAD:
				flush_node_list(math_link(numerator(p)));
				flush_node_list(math_link(denominator(p)));
				free_node(p, FRACTION_NOAD_SIZE);
				goto done;

			default:
				confusion("flushing");
				break;
			}
			free_node(p, SMALL_NODE_SIZE);
			done:;	
		}
		p = q;
	}
}
Beispiel #13
0
void tex::short_display(ptr p)
	{
	int	n;

	for (; p != null; p = link(p)) {
		if (is_char_node(p)) {
			if (font(p) != font_in_short_display) {
				if (font(p) < FONT_BASE || font(p) > FONT_MAX) {
					print("*");
				} else {
					print_esc(null_str);
					print(font_id_text(font(p)));
				}
				print(" ");
				font_in_short_display = font(p);
			}
			print_ASCII(character(p));
		} else {
			switch (tex::type(p))
			{
			case HLIST_NODE:
			case VLIST_NODE: 
			case INS_NODE:
			case WHATSIT_NODE:
			case MARK_NODE:
			case ADJUST_NODE:
			case UNSET_NODE:
				print("[]");
				break;

			case RULE_NODE:
				print("|");
				break;

			case GLUE_NODE:
				if (glue_ptr(p) != zero_glue)
					print(" ");
				break;

			case MATH_NODE:
				print("$");
				break;

			case LIGATURE_NODE:
				short_display(lig_ptr(p));
				break;

			case DISC_NODE:
				short_display(pre_break(p));
				short_display(post_break(p));
				n = replace_count(p);
				while (n > 0) {
					if (link(p) != null)
						p = link(p);
					decr(n);
				}
				break;

			default:
				break;
			}
		}
	}
}