#!/usr/bin/env python
# -*- coding: utf-8 -*-

"""
transform the pep 380 implementation patch by greg ewing into a patch that
applies to current tip (and hopefully upcomming) of cpython default branch.

this code is released in the public domain by renaud blanch.

instructions:
1) get the patch from greg ewing
% wget http://www.cosc.canterbury.ac.nz/greg.ewing/python/yield-from/YieldFrom-Python3.1.2-rev5.zip
% unzip YieldFrom-Python3.1.2-rev5.zip
2) get current python
% hg clone http://hg.python.org/cpython/
% cd cpython
% hg update
3) apply the transformed patch to python source, i.e.:
% cat ../YieldFrom-Python3.1.2-rev5/YieldFrom-Python3.1.2-rev5.patch | python ../pep380_transform.py | patch -p 1
% ./configure
% make
"""


# imports ####################################################################

import sys
import re


# constants ##################################################################

DIFF_PREFIX = "diff -r 444212f66719"

FILES_TO_DETAB = [
	'Objects/frameobject.c',
	'Objects/genobject.c',
	'Python/ceval.c',
	'Python/compile.c',
	'Python/symtable.c',
]
TO_DETAB_RE = r"^([+\-\ ])(\t+)"

SYMTABLE_TO_REPLACE = {
	'@@ -1158,13 +1158,6 @@ symtable_visit_stmt(struct symtable *st,\n':
	'@@ -1158,14 +1158,6 @@ symtable_visit_stmt(struct symtable *st,\n',

	'-                    PyErr_SyntaxLocation(st->st_filename,\n':
	'-                PyErr_SyntaxLocationEx(st->st_filename,\n',
	
	'-                             s->lineno);\n':
	'-                                       s->lineno,\n' + \
	'-                                       s->col_offset);\n',

	'                 st->st_cur->ste_generator = 1;\n':
	'         st->st_cur->ste_generator = 1;\n',

	'-                PyErr_SyntaxLocation(st->st_filename,\n':
	'-            PyErr_SyntaxLocationEx(st->st_filename,\n',
	
	'-                         e->lineno);\n':
	'-                                   e->lineno, e->col_offset);\n',
	
	'         case Compare_kind:\n':
	'     case Compare_kind:\n',
}

FRAMEOBJECT_TO_REPLACE = {
	'     {"f_builtins",	T_OBJECT,	OFF(f_builtins),READONLY},\n':
	'     {"f_builtins",      T_OBJECT,       OFF(f_builtins),READONLY},\n',
	
	'     {"f_globals",	T_OBJECT,	OFF(f_globals),	READONLY},\n':
	'     {"f_globals",       T_OBJECT,       OFF(f_globals), READONLY},\n',
	
	'     {"f_lasti",	T_INT,		OFF(f_lasti),	READONLY},\n':
	'     {"f_lasti",         T_INT,          OFF(f_lasti),   READONLY},\n',
	
	'+    {"f_yieldfrom",	T_OBJECT,       OFF(f_yieldfrom),READONLY},\n':
	'+    {"f_yieldfrom",     T_OBJECT,       OFF(f_yieldfrom),READONLY},\n',
	
	'     {NULL}	/* Sentinel */\n':
	'     {NULL}      /* Sentinel */\n',
}


# patch the patch ############################################################

for line in sys.stdin:
	if line.startswith(DIFF_PREFIX):
		filename = line.strip().split()[-1]
	
	if filename in FILES_TO_DETAB:
		if re.match(TO_DETAB_RE, line):
			words = re.split(TO_DETAB_RE, line)
			words[2] = words[2].replace("\t", " " * 4)
			line = "".join(words)
	
	if filename == "Python/symtable.c":
		if line in SYMTABLE_TO_REPLACE:
			line = SYMTABLE_TO_REPLACE[line]
	
	if filename == "Objects/frameobject.c":
		if line in FRAMEOBJECT_TO_REPLACE:
			line = FRAMEOBJECT_TO_REPLACE[line]
		
	sys.stdout.write(line)
