From 508b4902f6e6df7387b617a67c6fe5e248ee2c38 Mon Sep 17 00:00:00 2001 From: Matthias Andreas Benkard Date: Thu, 12 Jun 2008 20:27:29 +0200 Subject: Add class MLKDynamicContext. --- GNUmakefile | 4 ++-- MLKDynamicContext.h | 26 ++++++++++++++++++++++ MLKDynamicContext.m | 63 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 91 insertions(+), 2 deletions(-) create mode 100644 MLKDynamicContext.h create mode 100644 MLKDynamicContext.m diff --git a/GNUmakefile b/GNUmakefile index 53176e7..4655041 100644 --- a/GNUmakefile +++ b/GNUmakefile @@ -18,8 +18,8 @@ include $(GNUSTEP_MAKEFILES)/common.make TOOL_NAME = etoilisp -etoilisp_OBJC_FILES = MLKCons.m MLKEnvironment.m MLKLinkedList.m \ - MLKLispValue.m MLKSymbol.m \ +etoilisp_OBJC_FILES = MLKCons.m MLKDynamicContext.m MLKEnvironment.m \ + MLKLinkedList.m MLKLispValue.m MLKSymbol.m \ MLKUndefinedVariableException.m BUNDLE_NAME = Test diff --git a/MLKDynamicContext.h b/MLKDynamicContext.h new file mode 100644 index 0000000..f515901 --- /dev/null +++ b/MLKDynamicContext.h @@ -0,0 +1,26 @@ +/* -*- mode: objc; coding: utf-8 -*- */ +/* Copyright 2008, Matthias Benkard. */ + +@class MLKClosure, MLKEnvironment, NSLinkedList, NSMutableDictionary, NSString; + + +@interface MLKDynamicContext +{ + MLKEnvironment *_conditionHandlers; + MLKEnvironment *_restarts; + MLKClosure *_currentConditionHandler; + MLKEnvironment *_environment; + MLKDynamicContext *_parent; +} + +-(MLKDynamicContext *) initWithParent:(MLKDynamicContext *)aContext + variables:(NSDictionary *)vars + handlers:(NSDictionary *)handlers + restarts:(NSDictionary *)restarts + currentHandler:(MLKClosure *)handler; + +-(MLKDynamicContext *) pushContext; + ++(MLKDynamicContext *) currentContext; ++(MLKDynamicContext *) popContext; +@end diff --git a/MLKDynamicContext.m b/MLKDynamicContext.m new file mode 100644 index 0000000..2d8312f --- /dev/null +++ b/MLKDynamicContext.m @@ -0,0 +1,63 @@ +/* -*- mode: objc; coding: utf-8 -*- */ +/* Copyright 2008, Matthias Benkard. */ + +#import +#import +#import + +#import "MLKDynamicContext.h" +#import "MLKEnvironment.h" +#import "MLKLinkedList.h" + + +#define MAKE_ENVIRONMENT(variable, parent, parent_member) \ + (variable \ + ? (id) [[MLKEnvironment alloc] \ + initWithParent:(parent \ + ? (id) parent_member \ + : nil) \ + bindings:vars] \ + : (id) (parent ? (id) parent_member : nil)); + + +@implementation MLKDynamicContext +-(MLKDynamicContext *) initWithParent:(MLKDynamicContext *)aContext + variables:(NSDictionary *)vars + handlers:(NSDictionary *)handlers + restarts:(NSDictionary *)restarts + currentHandler:(MLKClosure *)handler +{ + _parent = (aContext ? aContext : [MLKDynamicContext currentContext]); + _environment = MAKE_ENVIRONMENT(vars, _parent, _parent->_environment); + _conditionHandlers = MAKE_ENVIRONMENT(handlers, + _parent, + _parent->_conditionHandlers); + _restarts = MAKE_ENVIRONMENT(restarts, _parent, _parent->_restarts); + _currentConditionHandler = (handler + ? (id) handler + : (_parent + ? (id) _parent->_currentConditionHandler + : nil)); + return self; +} + +-(MLKDynamicContext *) pushContext +{ + return [[[NSThread currentThread] threadDictionary] + objectForKey:@"MLKDynamicContext"]; +} + ++(MLKDynamicContext *) currentContext +{ + return [[[NSThread currentThread] threadDictionary] + objectForKey:@"MLKDynamicContext"]; +} + ++(MLKDynamicContext *) popContext +{ + MLKDynamicContext *context = [self currentContext]; + [[[NSThread currentThread] threadDictionary] setObject:context->_parent + forKey:@"MLKDynamicContext"]; + return context; +} +@end -- cgit v1.2.3