github.com/pygolin/runtime@v0.0.0-20201208210830-a62e3cd39798/builtin_types.go (about) 1 // Copyright 2016 Google Inc. All Rights Reserved. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package runtime 16 17 import ( 18 "bytes" 19 "fmt" 20 "math" 21 "math/big" 22 "strings" 23 "unicode" 24 ) 25 26 var ( 27 // Builtins contains all of the Python built-in identifiers. 28 Builtins = NewDict() 29 builtinStr = NewStr("__builtin__") 30 // ExceptionTypes contains all builtin exception types. 31 ExceptionTypes []*Type 32 // EllipsisType is the object representing the Python 'ellipsis' type 33 EllipsisType = newSimpleType("ellipsis", ObjectType) 34 // Ellipsis is the singleton ellipsis object representing the Python 35 // 'Ellipsis' object. 36 Ellipsis = &Object{typ: EllipsisType} 37 // NoneType is the object representing the Python 'NoneType' type. 38 NoneType = newSimpleType("NoneType", ObjectType) 39 // None is the singleton NoneType object representing the Python 'None' 40 // object. 41 None = &Object{typ: NoneType} 42 // NotImplementedType is the object representing the Python 43 // 'NotImplementedType' object. 44 NotImplementedType = newSimpleType("NotImplementedType", ObjectType) 45 // NotImplemented is the singleton NotImplementedType object 46 // representing the Python 'NotImplemented' object. 47 NotImplemented = newObject(NotImplementedType) 48 unboundLocalType = newSimpleType("UnboundLocalType", ObjectType) 49 // UnboundLocal is a singleton held by local variables in generated 50 // code before they are bound. 51 UnboundLocal = newObject(unboundLocalType) 52 ) 53 54 func ellipsisRepr(*Frame, *Object) (*Object, *BaseException) { 55 return NewStr("Ellipsis").ToObject(), nil 56 } 57 58 func noneRepr(*Frame, *Object) (*Object, *BaseException) { 59 return NewStr("None").ToObject(), nil 60 } 61 62 func notImplementedRepr(*Frame, *Object) (*Object, *BaseException) { 63 return NewStr("NotImplemented").ToObject(), nil 64 } 65 66 func initEllipsisType(map[string]*Object) { 67 EllipsisType.flags &= ^(typeFlagInstantiable | typeFlagBasetype) 68 EllipsisType.slots.Repr = &unaryOpSlot{ellipsisRepr} 69 } 70 71 func initNoneType(map[string]*Object) { 72 NoneType.flags &= ^(typeFlagInstantiable | typeFlagBasetype) 73 NoneType.slots.Repr = &unaryOpSlot{noneRepr} 74 } 75 76 func initNotImplementedType(map[string]*Object) { 77 NotImplementedType.flags &= ^(typeFlagInstantiable | typeFlagBasetype) 78 NotImplementedType.slots.Repr = &unaryOpSlot{notImplementedRepr} 79 } 80 81 func initUnboundLocalType(map[string]*Object) { 82 unboundLocalType.flags &= ^(typeFlagInstantiable | typeFlagBasetype) 83 } 84 85 type typeState int 86 87 const ( 88 typeStateNotReady typeState = iota 89 typeStateInitializing 90 typeStateReady 91 ) 92 93 type builtinTypeInit func(map[string]*Object) 94 95 type builtinTypeInfo struct { 96 state typeState 97 init builtinTypeInit 98 global bool 99 } 100 101 var builtinTypes = map[*Type]*builtinTypeInfo{ 102 ArithmeticErrorType: {global: true}, 103 AssertionErrorType: {global: true}, 104 AttributeErrorType: {global: true}, 105 BaseExceptionType: {init: initBaseExceptionType, global: true}, 106 BaseStringType: {init: initBaseStringType, global: true}, 107 BoolType: {init: initBoolType, global: true}, 108 ByteArrayType: {init: initByteArrayType, global: true}, 109 BytesWarningType: {global: true}, 110 callableIteratorType: {init: initCallableIteratorType}, 111 CodeType: {}, 112 ComplexType: {init: initComplexType, global: true}, 113 ClassMethodType: {init: initClassMethodType, global: true}, 114 DeprecationWarningType: {global: true}, 115 dictItemIteratorType: {init: initDictItemIteratorType}, 116 dictKeyIteratorType: {init: initDictKeyIteratorType}, 117 dictValueIteratorType: {init: initDictValueIteratorType}, 118 DictType: {init: initDictType, global: true}, 119 EllipsisType: {init: initEllipsisType, global: true}, 120 enumerateType: {init: initEnumerateType, global: true}, 121 EnvironmentErrorType: {global: true}, 122 EOFErrorType: {global: true}, 123 ExceptionType: {global: true}, 124 FileType: {init: initFileType, global: true}, 125 FloatType: {init: initFloatType, global: true}, 126 FrameType: {init: initFrameType}, 127 FrozenSetType: {init: initFrozenSetType, global: true}, 128 FunctionType: {init: initFunctionType}, 129 FutureWarningType: {global: true}, 130 GeneratorType: {init: initGeneratorType}, 131 ImportErrorType: {global: true}, 132 ImportWarningType: {global: true}, 133 IndexErrorType: {global: true}, 134 IntType: {init: initIntType, global: true}, 135 IOErrorType: {global: true}, 136 KeyboardInterruptType: {global: true}, 137 KeyErrorType: {global: true}, 138 listIteratorType: {init: initListIteratorType}, 139 ListType: {init: initListType, global: true}, 140 LongType: {init: initLongType, global: true}, 141 LookupErrorType: {global: true}, 142 MemoryErrorType: {global: true}, 143 MethodType: {init: initMethodType}, 144 ModuleType: {init: initModuleType}, 145 NameErrorType: {global: true}, 146 nativeBoolMetaclassType: {init: initNativeBoolMetaclassType}, 147 nativeFuncType: {init: initNativeFuncType}, 148 nativeMetaclassType: {init: initNativeMetaclassType}, 149 nativeSliceType: {init: initNativeSliceType}, 150 nativeType: {init: initNativeType}, 151 NoneType: {init: initNoneType, global: true}, 152 NotImplementedErrorType: {global: true}, 153 NotImplementedType: {init: initNotImplementedType, global: true}, 154 ObjectType: {init: initObjectType, global: true}, 155 OSErrorType: {global: true}, 156 OverflowErrorType: {global: true}, 157 PendingDeprecationWarningType: {global: true}, 158 PropertyType: {init: initPropertyType, global: true}, 159 rangeIteratorType: {init: initRangeIteratorType, global: true}, 160 ReferenceErrorType: {global: true}, 161 RuntimeErrorType: {global: true}, 162 RuntimeWarningType: {global: true}, 163 seqIteratorType: {init: initSeqIteratorType}, 164 SetType: {init: initSetType, global: true}, 165 sliceIteratorType: {init: initSliceIteratorType}, 166 SliceType: {init: initSliceType, global: true}, 167 StandardErrorType: {global: true}, 168 StaticMethodType: {init: initStaticMethodType, global: true}, 169 StopIterationType: {global: true}, 170 StrType: {init: initStrType, global: true}, 171 superType: {init: initSuperType, global: true}, 172 SyntaxErrorType: {global: true}, 173 SyntaxWarningType: {global: true}, 174 SystemErrorType: {global: true}, 175 SystemExitType: {global: true, init: initSystemExitType}, 176 TracebackType: {init: initTracebackType}, 177 TupleType: {init: initTupleType, global: true}, 178 TypeErrorType: {global: true}, 179 TypeType: {init: initTypeType, global: true}, 180 UnboundLocalErrorType: {global: true}, 181 unboundLocalType: {init: initUnboundLocalType}, 182 UnicodeDecodeErrorType: {global: true}, 183 UnicodeEncodeErrorType: {global: true}, 184 UnicodeErrorType: {global: true}, 185 UnicodeType: {init: initUnicodeType, global: true}, 186 UnicodeWarningType: {global: true}, 187 UserWarningType: {global: true}, 188 ValueErrorType: {global: true}, 189 WarningType: {global: true}, 190 WeakRefType: {init: initWeakRefType}, 191 xrangeType: {init: initXRangeType, global: true}, 192 ZeroDivisionErrorType: {global: true}, 193 } 194 195 func initBuiltinType(typ *Type, info *builtinTypeInfo) { 196 if info.state == typeStateReady { 197 return 198 } 199 if info.state == typeStateInitializing { 200 logFatal(fmt.Sprintf("cycle in type initialization for: %s", typ.name)) 201 } 202 info.state = typeStateInitializing 203 for _, base := range typ.bases { 204 baseInfo, ok := builtinTypes[base] 205 if !ok { 206 logFatal(fmt.Sprintf("base type not registered for: %s", typ.name)) 207 } 208 initBuiltinType(base, baseInfo) 209 } 210 prepareBuiltinType(typ, info.init) 211 info.state = typeStateReady 212 if typ.isSubclass(BaseExceptionType) { 213 ExceptionTypes = append(ExceptionTypes, typ) 214 } 215 } 216 217 func builtinAbs(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 218 if raised := checkFunctionArgs(f, "abs", args, ObjectType); raised != nil { 219 return nil, raised 220 } 221 return Abs(f, args[0]) 222 } 223 224 func builtinMapFn(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 225 argc := len(args) 226 if argc < 2 { 227 return nil, f.RaiseType(TypeErrorType, "map() requires at least two args") 228 } 229 result := make([]*Object, 0, 2) 230 z, raised := zipLongest(f, args[1:]) 231 if raised != nil { 232 return nil, raised 233 } 234 for _, tuple := range z { 235 if args[0] == None { 236 if argc == 2 { 237 result = append(result, tuple[0]) 238 } else { 239 result = append(result, NewTuple(tuple...).ToObject()) 240 } 241 } else { 242 ret, raised := args[0].Call(f, tuple, nil) 243 if raised != nil { 244 return nil, raised 245 } 246 result = append(result, ret) 247 } 248 } 249 250 return NewList(result...).ToObject(), nil 251 } 252 253 func builtinFilter(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 254 if raised := checkMethodArgs(f, "filter", args, ObjectType, ObjectType); raised != nil { 255 return nil, raised 256 } 257 fn := args[0] 258 l := args[1] 259 filterFunc := IsTrue 260 if fn != None { 261 filterFunc = func(f *Frame, o *Object) (bool, *BaseException) { 262 result, raised := fn.Call(f, Args{o}, nil) 263 if raised != nil { 264 return false, raised 265 } 266 return IsTrue(f, result) 267 } 268 } 269 switch { 270 // CPython will return the same type if the second type is tuple or string, else return a list. 271 case l.isInstance(TupleType): 272 result := make([]*Object, 0) 273 for _, item := range toTupleUnsafe(l).elems { 274 ret, raised := filterFunc(f, item) 275 if raised != nil { 276 return nil, raised 277 } 278 if ret { 279 result = append(result, item) 280 } 281 } 282 return NewTuple(result...).ToObject(), nil 283 case l.isInstance(StrType): 284 if fn == None { 285 return l, nil 286 } 287 var result bytes.Buffer 288 for _, item := range []byte(toStrUnsafe(l).Value()) { 289 ret, raised := filterFunc(f, NewStr(string(item)).ToObject()) 290 if raised != nil { 291 return nil, raised 292 } 293 if ret { 294 result.WriteByte(item) 295 } 296 } 297 return NewStr(result.String()).ToObject(), nil 298 case l.isInstance(UnicodeType): 299 if fn == None { 300 return l, nil 301 } 302 var result []rune 303 for _, item := range toUnicodeUnsafe(l).Value() { 304 ret, raised := filterFunc(f, NewUnicodeFromRunes([]rune{item}).ToObject()) 305 if raised != nil { 306 return nil, raised 307 } 308 if ret { 309 result = append(result, item) 310 } 311 } 312 return NewUnicodeFromRunes(result).ToObject(), nil 313 default: 314 result := make([]*Object, 0) 315 raised := seqForEach(f, l, func(item *Object) (raised *BaseException) { 316 ret, raised := filterFunc(f, item) 317 if raised != nil { 318 return raised 319 } 320 if ret { 321 result = append(result, item) 322 } 323 return nil 324 }) 325 if raised != nil { 326 return nil, raised 327 } 328 return NewList(result...).ToObject(), nil 329 } 330 } 331 332 func builtinAll(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 333 if raised := checkFunctionArgs(f, "all", args, ObjectType); raised != nil { 334 return nil, raised 335 } 336 pred := func(o *Object) (bool, *BaseException) { 337 ret, raised := IsTrue(f, o) 338 if raised != nil { 339 return false, raised 340 } 341 return !ret, nil 342 } 343 foundFalseItem, raised := seqFindFirst(f, args[0], pred) 344 if raised != nil { 345 return nil, raised 346 } 347 return GetBool(!foundFalseItem).ToObject(), raised 348 } 349 350 func builtinAny(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 351 if raised := checkFunctionArgs(f, "any", args, ObjectType); raised != nil { 352 return nil, raised 353 } 354 pred := func(o *Object) (bool, *BaseException) { 355 ret, raised := IsTrue(f, o) 356 if raised != nil { 357 return false, raised 358 } 359 return ret, nil 360 } 361 foundTrueItem, raised := seqFindFirst(f, args[0], pred) 362 if raised != nil { 363 return nil, raised 364 } 365 return GetBool(foundTrueItem).ToObject(), raised 366 } 367 368 func builtinBin(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 369 if raised := checkFunctionArgs(f, "bin", args, ObjectType); raised != nil { 370 return nil, raised 371 } 372 index, raised := Index(f, args[0]) 373 if raised != nil { 374 return nil, raised 375 } 376 if index == nil { 377 format := "%s object cannot be interpreted as an index" 378 return nil, f.RaiseType(TypeErrorType, fmt.Sprintf(format, args[0].typ.Name())) 379 } 380 return NewStr(numberToBase("0b", 2, index)).ToObject(), nil 381 } 382 383 func builtinCallable(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 384 if raised := checkFunctionArgs(f, "callable", args, ObjectType); raised != nil { 385 return nil, raised 386 } 387 o := args[0] 388 if call := o.Type().slots.Call; call == nil { 389 return False.ToObject(), nil 390 } 391 return True.ToObject(), nil 392 } 393 394 func builtinChr(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 395 if raised := checkFunctionArgs(f, "chr", args, IntType); raised != nil { 396 return nil, raised 397 } 398 i := toIntUnsafe(args[0]).Value() 399 if i < 0 || i > 255 { 400 return nil, f.RaiseType(ValueErrorType, "chr() arg not in range(256)") 401 } 402 return NewStr(string([]byte{byte(i)})).ToObject(), nil 403 } 404 405 func builtinCmp(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 406 if raised := checkFunctionArgs(f, "cmp", args, ObjectType, ObjectType); raised != nil { 407 return nil, raised 408 } 409 return Compare(f, args[0], args[1]) 410 } 411 412 func builtinDelAttr(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 413 if raised := checkFunctionArgs(f, "delattr", args, ObjectType, StrType); raised != nil { 414 return nil, raised 415 } 416 return None, DelAttr(f, args[0], toStrUnsafe(args[1])) 417 } 418 419 func builtinDir(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 420 // TODO: Support __dir__. 421 if raised := checkFunctionArgs(f, "dir", args, ObjectType); raised != nil { 422 return nil, raised 423 } 424 d := NewDict() 425 o := args[0] 426 switch { 427 case o.isInstance(TypeType): 428 for _, t := range toTypeUnsafe(o).mro { 429 if raised := d.Update(f, t.Dict().ToObject()); raised != nil { 430 return nil, raised 431 } 432 } 433 case o.isInstance(ModuleType): 434 d.Update(f, o.Dict().ToObject()) 435 default: 436 d = NewDict() 437 if dict := o.Dict(); dict != nil { 438 if raised := d.Update(f, dict.ToObject()); raised != nil { 439 return nil, raised 440 } 441 } 442 for _, t := range o.typ.mro { 443 if raised := d.Update(f, t.Dict().ToObject()); raised != nil { 444 return nil, raised 445 } 446 } 447 } 448 l := d.Keys(f) 449 if raised := l.Sort(f); raised != nil { 450 return nil, raised 451 } 452 return l.ToObject(), nil 453 } 454 455 func builtinDivMod(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 456 if raised := checkFunctionArgs(f, "divmod", args, ObjectType, ObjectType); raised != nil { 457 return nil, raised 458 } 459 return DivMod(f, args[0], args[1]) 460 } 461 462 func builtinFrame(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 463 if raised := checkFunctionArgs(f, "__frame__", args); raised != nil { 464 return nil, raised 465 } 466 f.taken = true 467 return f.ToObject(), nil 468 } 469 470 func builtinGetAttr(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 471 expectedTypes := []*Type{ObjectType, StrType, ObjectType} 472 argc := len(args) 473 if argc == 2 { 474 expectedTypes = expectedTypes[:2] 475 } 476 if raised := checkFunctionArgs(f, "getattr", args, expectedTypes...); raised != nil { 477 return nil, raised 478 } 479 var def *Object 480 if argc == 3 { 481 def = args[2] 482 } 483 return GetAttr(f, args[0], toStrUnsafe(args[1]), def) 484 } 485 486 func builtinGlobals(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 487 if raised := checkFunctionArgs(f, "globals", args); raised != nil { 488 return nil, raised 489 } 490 return f.globals.ToObject(), nil 491 } 492 493 func builtinHasAttr(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 494 if raised := checkFunctionArgs(f, "hasattr", args, ObjectType, StrType); raised != nil { 495 return nil, raised 496 } 497 if _, raised := GetAttr(f, args[0], toStrUnsafe(args[1]), nil); raised != nil { 498 if raised.isInstance(AttributeErrorType) { 499 f.RestoreExc(nil, nil) 500 return False.ToObject(), nil 501 } 502 return nil, raised 503 } 504 return True.ToObject(), nil 505 } 506 507 func builtinHash(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 508 if raised := checkFunctionArgs(f, "hash", args, ObjectType); raised != nil { 509 return nil, raised 510 } 511 h, raised := Hash(f, args[0]) 512 if raised != nil { 513 return nil, raised 514 } 515 return h.ToObject(), nil 516 } 517 518 func builtinHex(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 519 // In Python3 we would call __index__ similarly to builtinBin(). 520 if raised := checkFunctionArgs(f, "hex", args, ObjectType); raised != nil { 521 return nil, raised 522 } 523 return Hex(f, args[0]) 524 } 525 526 func builtinID(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 527 if raised := checkFunctionArgs(f, "id", args, ObjectType); raised != nil { 528 return nil, raised 529 } 530 return NewInt(int(uintptr(args[0].toPointer()))).ToObject(), nil 531 } 532 533 func builtinIsInstance(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 534 if raised := checkFunctionArgs(f, "isinstance", args, ObjectType, ObjectType); raised != nil { 535 return nil, raised 536 } 537 ret, raised := IsInstance(f, args[0], args[1]) 538 if raised != nil { 539 return nil, raised 540 } 541 return GetBool(ret).ToObject(), nil 542 } 543 544 func builtinIsSubclass(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 545 if raised := checkFunctionArgs(f, "issubclass", args, ObjectType, ObjectType); raised != nil { 546 return nil, raised 547 } 548 ret, raised := IsSubclass(f, args[0], args[1]) 549 if raised != nil { 550 return nil, raised 551 } 552 return GetBool(ret).ToObject(), nil 553 } 554 555 func builtinIter(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 556 argc := len(args) 557 expectedTypes := []*Type{ObjectType, ObjectType} 558 if argc == 1 { 559 expectedTypes = expectedTypes[:1] 560 } 561 if raised := checkFunctionArgs(f, "iter", args, expectedTypes...); raised != nil { 562 return nil, raised 563 } 564 if argc == 1 { 565 return Iter(f, args[0]) 566 } 567 return IterCallable(f, args[0], args[1]) 568 } 569 570 func builtinLen(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 571 if raised := checkFunctionArgs(f, "len", args, ObjectType); raised != nil { 572 return nil, raised 573 } 574 ret, raised := Len(f, args[0]) 575 if raised != nil { 576 return nil, raised 577 } 578 return ret.ToObject(), nil 579 } 580 581 func builtinMax(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 582 return builtinMinMax(f, true, args, kwargs) 583 } 584 585 func builtinMin(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 586 return builtinMinMax(f, false, args, kwargs) 587 } 588 589 func builtinNext(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 590 if raised := checkFunctionArgs(f, "next", args, ObjectType); raised != nil { 591 return nil, raised 592 } 593 ret, raised := Next(f, args[0]) 594 if raised != nil { 595 return nil, raised 596 } 597 if ret != nil { 598 return ret, nil 599 } 600 return nil, f.Raise(StopIterationType.ToObject(), nil, nil) 601 } 602 603 func builtinOct(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 604 // In Python3 we would call __index__ similarly to builtinBin(). 605 if raised := checkFunctionArgs(f, "oct", args, ObjectType); raised != nil { 606 return nil, raised 607 } 608 return Oct(f, args[0]) 609 } 610 611 func builtinOpen(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 612 return FileType.Call(f, args, kwargs) 613 } 614 615 func builtinOrd(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 616 const lenMsg = "ord() expected a character, but string of length %d found" 617 if raised := checkFunctionArgs(f, "ord", args, BaseStringType); raised != nil { 618 return nil, raised 619 } 620 o := args[0] 621 var result int 622 if o.isInstance(StrType) { 623 s := toStrUnsafe(o).Value() 624 if numChars := len(s); numChars != 1 { 625 return nil, f.RaiseType(ValueErrorType, fmt.Sprintf(lenMsg, numChars)) 626 } 627 result = int(([]byte(s))[0]) 628 } else { 629 s := toUnicodeUnsafe(o).Value() 630 if numChars := len(s); numChars != 1 { 631 return nil, f.RaiseType(ValueErrorType, fmt.Sprintf(lenMsg, numChars)) 632 } 633 result = int(s[0]) 634 } 635 return NewInt(result).ToObject(), nil 636 } 637 638 func builtinPower(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 639 expectedTypes := []*Type{ObjectType, ObjectType} 640 if len(args) == 3 { 641 return nil, f.RaiseType(NotImplementedErrorType, "third parameter is not supported now") 642 } 643 if raised := checkFunctionArgs(f, "pow", args, expectedTypes...); raised != nil { 644 return nil, raised 645 } 646 return Pow(f, args[0], args[1]) 647 } 648 649 func builtinPrint(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 650 sep := " " 651 end := "\n" 652 file := Stdout 653 for _, kwarg := range kwargs { 654 switch kwarg.Name { 655 case "sep": 656 kwsep, raised := ToStr(f, kwarg.Value) 657 if raised != nil { 658 return nil, raised 659 } 660 sep = kwsep.Value() 661 case "end": 662 kwend, raised := ToStr(f, kwarg.Value) 663 if raised != nil { 664 return nil, raised 665 } 666 end = kwend.Value() 667 case "file": 668 // TODO: need to map Python sys.stdout, sys.stderr etc. to os.Stdout, 669 // os.Stderr, but for other file-like objects would need to recover 670 // to the file descriptor probably 671 } 672 } 673 return nil, pyPrint(f, args, sep, end, file) 674 } 675 676 func builtinRange(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 677 r, raised := xrangeType.Call(f, args, nil) 678 if raised != nil { 679 return nil, raised 680 } 681 return ListType.Call(f, []*Object{r}, nil) 682 } 683 684 func builtinRawInput(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 685 if len(args) > 1 { 686 msg := fmt.Sprintf("[raw_]input expcted at most 1 arguments, got %d", len(args)) 687 return nil, f.RaiseType(TypeErrorType, msg) 688 } 689 690 if Stdin == nil { 691 msg := fmt.Sprintf("[raw_]input: lost sys.stdin") 692 return nil, f.RaiseType(RuntimeErrorType, msg) 693 } 694 695 if Stdout == nil { 696 msg := fmt.Sprintf("[raw_]input: lost sys.stdout") 697 return nil, f.RaiseType(RuntimeErrorType, msg) 698 } 699 700 if len(args) == 1 { 701 err := pyPrint(f, args, "", "", Stdout) 702 if err != nil { 703 return nil, err 704 } 705 } 706 707 line, err := Stdin.reader.ReadString('\n') 708 if err != nil { 709 return nil, f.RaiseType(EOFErrorType, "EOF when reading a line") 710 } 711 line = strings.TrimRight(line, "\n") 712 return NewStr(line).ToObject(), nil 713 } 714 715 func builtinRepr(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 716 if raised := checkFunctionArgs(f, "repr", args, ObjectType); raised != nil { 717 return nil, raised 718 } 719 s, raised := Repr(f, args[0]) 720 if raised != nil { 721 return nil, raised 722 } 723 return s.ToObject(), nil 724 } 725 726 func builtinRound(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 727 argc := len(args) 728 expectedTypes := []*Type{ObjectType, ObjectType} 729 if argc == 1 { 730 expectedTypes = expectedTypes[:1] 731 } 732 if raised := checkFunctionArgs(f, "round", args, expectedTypes...); raised != nil { 733 return nil, raised 734 } 735 ndigits := 0 736 if argc > 1 { 737 var raised *BaseException 738 if ndigits, raised = IndexInt(f, args[1]); raised != nil { 739 return nil, raised 740 } 741 } 742 number, isFloat := floatCoerce(args[0]) 743 744 if !isFloat { 745 return nil, f.RaiseType(TypeErrorType, "a float is required") 746 } 747 748 if math.IsNaN(number) || math.IsInf(number, 0) || number == 0.0 { 749 return NewFloat(number).ToObject(), nil 750 } 751 752 neg := false 753 if number < 0 { 754 neg = true 755 number = -number 756 } 757 pow := math.Pow(10.0, float64(ndigits)) 758 result := math.Floor(number*pow+0.5) / pow 759 if neg { 760 result = -result 761 } 762 return NewFloat(result).ToObject(), nil 763 } 764 765 func builtinSetAttr(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 766 if raised := checkFunctionArgs(f, "setattr", args, ObjectType, StrType, ObjectType); raised != nil { 767 return nil, raised 768 } 769 return None, SetAttr(f, args[0], toStrUnsafe(args[1]), args[2]) 770 } 771 772 func builtinSorted(f *Frame, args Args, kwargs KWArgs) (*Object, *BaseException) { 773 // TODO: Support (cmp=None, key=None, reverse=False) 774 if raised := checkFunctionArgs(f, "sorted", args, ObjectType); raised != nil { 775 return nil, raised 776 } 777 result, raised := ListType.Call(f, Args{args[0]}, nil) 778 if raised != nil { 779 return nil, raised 780 } 781 toListUnsafe(result).Sort(f) 782 // Implement reverse. 783 reverse, raised := IsTrue(f, kwargs.get("reverse", None)) 784 if raised != nil { 785 return nil, raised 786 } 787 if reverse { 788 toListUnsafe(result).Reverse() 789 } 790 return result, nil 791 } 792 793 func builtinSum(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 794 argc := len(args) 795 expectedTypes := []*Type{ObjectType, ObjectType} 796 if argc == 1 { 797 expectedTypes = expectedTypes[:1] 798 } 799 if raised := checkFunctionArgs(f, "sum", args, expectedTypes...); raised != nil { 800 return nil, raised 801 } 802 var result *Object 803 if argc > 1 { 804 if args[1].typ == StrType { 805 return nil, f.RaiseType(TypeErrorType, "sum() can't sum strings [use ''.join(seq) instead]") 806 } 807 result = args[1] 808 } else { 809 result = NewInt(0).ToObject() 810 } 811 raised := seqForEach(f, args[0], func(o *Object) (raised *BaseException) { 812 result, raised = Add(f, result, o) 813 return raised 814 }) 815 816 if raised != nil { 817 return nil, raised 818 } 819 return result, nil 820 } 821 822 func builtinUniChr(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 823 if raised := checkFunctionArgs(f, "unichr", args, IntType); raised != nil { 824 return nil, raised 825 } 826 i := toIntUnsafe(args[0]).Value() 827 if i < 0 || i > unicode.MaxRune { 828 return nil, f.RaiseType(ValueErrorType, fmt.Sprintf("unichr() arg not in range(0x%x)", unicode.MaxRune)) 829 } 830 return NewUnicodeFromRunes([]rune{rune(i)}).ToObject(), nil 831 } 832 833 func builtinZip(f *Frame, args Args, _ KWArgs) (*Object, *BaseException) { 834 argc := len(args) 835 if argc == 0 { 836 return NewList().ToObject(), nil 837 } 838 result := make([]*Object, 0, 2) 839 iters, raised := initIters(f, args) 840 if raised != nil { 841 return nil, raised 842 } 843 844 Outer: 845 for { 846 elems := make([]*Object, argc) 847 for i, iter := range iters { 848 elem, raised := Next(f, iter) 849 if raised != nil { 850 if raised.isInstance(StopIterationType) { 851 f.RestoreExc(nil, nil) 852 break Outer 853 } 854 return nil, raised 855 } 856 elems[i] = elem 857 } 858 result = append(result, NewTuple(elems...).ToObject()) 859 } 860 return NewList(result...).ToObject(), nil 861 } 862 863 func init() { 864 builtinMap := map[string]*Object{ 865 "__debug__": False.ToObject(), 866 "__frame__": newBuiltinFunction("__frame__", builtinFrame).ToObject(), 867 "abs": newBuiltinFunction("abs", builtinAbs).ToObject(), 868 "all": newBuiltinFunction("all", builtinAll).ToObject(), 869 "any": newBuiltinFunction("any", builtinAny).ToObject(), 870 "bin": newBuiltinFunction("bin", builtinBin).ToObject(), 871 "callable": newBuiltinFunction("callable", builtinCallable).ToObject(), 872 "chr": newBuiltinFunction("chr", builtinChr).ToObject(), 873 "cmp": newBuiltinFunction("cmp", builtinCmp).ToObject(), 874 "delattr": newBuiltinFunction("delattr", builtinDelAttr).ToObject(), 875 "dir": newBuiltinFunction("dir", builtinDir).ToObject(), 876 "divmod": newBuiltinFunction("divmod", builtinDivMod).ToObject(), 877 "Ellipsis": Ellipsis, 878 "False": False.ToObject(), 879 "filter": newBuiltinFunction("filter", builtinFilter).ToObject(), 880 "getattr": newBuiltinFunction("getattr", builtinGetAttr).ToObject(), 881 "globals": newBuiltinFunction("globals", builtinGlobals).ToObject(), 882 "hasattr": newBuiltinFunction("hasattr", builtinHasAttr).ToObject(), 883 "hash": newBuiltinFunction("hash", builtinHash).ToObject(), 884 "hex": newBuiltinFunction("hex", builtinHex).ToObject(), 885 "id": newBuiltinFunction("id", builtinID).ToObject(), 886 "isinstance": newBuiltinFunction("isinstance", builtinIsInstance).ToObject(), 887 "issubclass": newBuiltinFunction("issubclass", builtinIsSubclass).ToObject(), 888 "iter": newBuiltinFunction("iter", builtinIter).ToObject(), 889 "len": newBuiltinFunction("len", builtinLen).ToObject(), 890 "map": newBuiltinFunction("map", builtinMapFn).ToObject(), 891 "max": newBuiltinFunction("max", builtinMax).ToObject(), 892 "min": newBuiltinFunction("min", builtinMin).ToObject(), 893 "next": newBuiltinFunction("next", builtinNext).ToObject(), 894 "None": None, 895 "NotImplemented": NotImplemented, 896 "oct": newBuiltinFunction("oct", builtinOct).ToObject(), 897 "open": newBuiltinFunction("open", builtinOpen).ToObject(), 898 "ord": newBuiltinFunction("ord", builtinOrd).ToObject(), 899 "pow": newBuiltinFunction("pow", builtinPower).ToObject(), 900 "print": newBuiltinFunction("print", builtinPrint).ToObject(), 901 "range": newBuiltinFunction("range", builtinRange).ToObject(), 902 "raw_input": newBuiltinFunction("raw_input", builtinRawInput).ToObject(), 903 "repr": newBuiltinFunction("repr", builtinRepr).ToObject(), 904 "round": newBuiltinFunction("round", builtinRound).ToObject(), 905 "setattr": newBuiltinFunction("setattr", builtinSetAttr).ToObject(), 906 "sorted": newBuiltinFunction("sorted", builtinSorted).ToObject(), 907 "sum": newBuiltinFunction("sum", builtinSum).ToObject(), 908 "True": True.ToObject(), 909 "unichr": newBuiltinFunction("unichr", builtinUniChr).ToObject(), 910 "zip": newBuiltinFunction("zip", builtinZip).ToObject(), 911 } 912 // Do type initialization in two phases so that we don't have to think 913 // about hard-to-understand cycles. 914 for typ, info := range builtinTypes { 915 initBuiltinType(typ, info) 916 if info.global { 917 builtinMap[typ.name] = typ.ToObject() 918 } 919 } 920 for name := range builtinMap { 921 InternStr(name) 922 } 923 Builtins = newStringDict(builtinMap) 924 } 925 926 // builtinMinMax implements the builtin min/max() functions. When doMax is 927 // true, the max is found, otherwise the min is found. There are two forms of 928 // the builtins. The first takes a single iterable argument and the result is 929 // the min/max of the elements of that sequence. The second form takes two or 930 // more args and returns the min/max of those. For more details see: 931 // https://docs.python.org/2/library/functions.html#min 932 func builtinMinMax(f *Frame, doMax bool, args Args, kwargs KWArgs) (*Object, *BaseException) { 933 name := "min" 934 if doMax { 935 name = "max" 936 } 937 if raised := checkFunctionVarArgs(f, name, args, ObjectType); raised != nil { 938 return nil, raised 939 } 940 keyFunc := kwargs.get("key", nil) 941 // selected is the min/max element found so far. 942 var selected, selectedKey *Object 943 partialFunc := func(o *Object) (raised *BaseException) { 944 oKey := o 945 if keyFunc != nil { 946 oKey, raised = keyFunc.Call(f, Args{o}, nil) 947 if raised != nil { 948 return raised 949 } 950 } 951 // sel dictates whether o is the new min/max. It defaults to 952 // true when selected == nil (we don't yet have a selection). 953 sel := true 954 if selected != nil { 955 result, raised := LT(f, selectedKey, oKey) 956 if raised != nil { 957 return raised 958 } 959 lt, raised := IsTrue(f, result) 960 if raised != nil { 961 return raised 962 } 963 // Select o when looking for max and selection < o, or 964 // when looking for min and o < selection. 965 sel = doMax && lt || !doMax && !lt 966 } 967 if sel { 968 selected = o 969 selectedKey = oKey 970 } 971 return nil 972 } 973 if len(args) == 1 { 974 // Take min/max of the single iterable arg passed. 975 if raised := seqForEach(f, args[0], partialFunc); raised != nil { 976 return nil, raised 977 } 978 if selected == nil { 979 return nil, f.RaiseType(ValueErrorType, fmt.Sprintf("%s() arg is an empty sequence", name)) 980 } 981 } else { 982 // Take min/max of the passed args. 983 for _, arg := range args { 984 if raised := partialFunc(arg); raised != nil { 985 return nil, raised 986 } 987 } 988 } 989 return selected, nil 990 } 991 992 // numberToBase implements the builtins "bin", "hex", and "oct". 993 // base must be between 2 and 36, and o must be an instance of 994 // IntType or LongType. 995 func numberToBase(prefix string, base int, o *Object) string { 996 z := big.Int{} 997 switch { 998 case o.isInstance(LongType): 999 z = toLongUnsafe(o).value 1000 case o.isInstance(IntType): 1001 z.SetInt64(int64(toIntUnsafe(o).Value())) 1002 default: 1003 panic("numberToBase requires an Int or Long argument") 1004 } 1005 s := z.Text(base) 1006 if s[0] == '-' { 1007 // Move the negative sign before the prefix. 1008 return "-" + prefix + s[1:] 1009 } 1010 return prefix + s 1011 } 1012 1013 // initIters return list of initiated Iter instances from the list of 1014 // iterables. 1015 func initIters(f *Frame, items []*Object) ([]*Object, *BaseException) { 1016 l := len(items) 1017 iters := make([]*Object, l) 1018 for i, arg := range items { 1019 iter, raised := Iter(f, arg) 1020 if raised != nil { 1021 return nil, raised 1022 } 1023 iters[i] = iter 1024 } 1025 return iters, nil 1026 } 1027 1028 // zipLongest return the list of aggregates elements from each of the 1029 // iterables. If the iterables are of uneven length, missing values are 1030 // filled-in with None. 1031 func zipLongest(f *Frame, args Args) ([][]*Object, *BaseException) { 1032 argc := len(args) 1033 result := make([][]*Object, 0, 2) 1034 iters, raised := initIters(f, args) 1035 if raised != nil { 1036 return nil, raised 1037 } 1038 1039 for { 1040 noItems := true 1041 elems := make([]*Object, argc) 1042 for i, iter := range iters { 1043 if iter == nil { 1044 continue 1045 } 1046 elem, raised := Next(f, iter) 1047 if raised != nil { 1048 if raised.isInstance(StopIterationType) { 1049 iters[i] = nil 1050 elems[i] = None 1051 f.RestoreExc(nil, nil) 1052 continue 1053 } 1054 return nil, raised 1055 } 1056 noItems = false 1057 elems[i] = elem 1058 } 1059 if noItems { 1060 break 1061 } 1062 result = append(result, elems) 1063 } 1064 return result, nil 1065 }